Character interaction temporal graph analysis
Project description
CIGA: Character Interaction Graph Analyzer
CIGA is a Python package designed for performing graph analysis on social interactions between individuals across time. It is a redesign of CharNet using igraph.
Simple example
import ciga as cg
import pandas as pd
import matplotlib.pyplot as plt
df = pd.DataFrame({
'Season': [1, 1, 1, 1],
'Episode': [1, 1, 1, 1],
'Scene': [1, 1, 2, 2],
'Line': [1, 2, 1, 2],
'Speaker': ['Sheldon', 'Leonard', 'Penny', 'Sheldon'],
'Listener': ['Leonard', 'Sheldon', 'Sheldon', 'Penny'],
'Words': ['Hello', 'Hi there', 'How are you?', 'Fine, thank you']
})
def weight_func(interaction):
return 1
position = ('Season', 'Episode', 'Scene', 'Line')
interactions = cg.prepare_data(data=df,
position=position,
source='Speaker',
target='Listener',
interaction='Words')
sub_interactions = cg.segment(interactions, start=(1, 1, 1, 1), end=(2, 1, 1, 1))
weights = cg.calculate_weights(sub_interactions, weight_func)
agg_weights = cg.agg_weights(data=weights,
position=position[:-1],
agg_func=lambda x: sum(x))
tg = cg.TGraph(data=agg_weights,
position=position[:-1],
directed=False)
graph = tg.get_graph((1, 1, 1))
fig, ax = plt.subplots()
cg.iplot(graph, target=ax)
plt.show()
res = cg.tgraph_degree(tg, weighted=True, w_normalized=False, normalized=True)
res.to_csv('results.csv')
More Examples
1. Basic Interaction Graph Creation and Visualization
import ciga as cg
import pandas as pd
import matplotlib.pyplot as plt
# Sample interaction data
data = pd.DataFrame({
'Time': [1, 1, 2, 2, 3],
'Source': ['Alice', 'Bob', 'Alice', 'Charlie', 'Bob'],
'Target': ['Bob', 'Alice', 'Charlie', 'Alice', 'Charlie'],
'Interaction': ['talk', 'talk', 'nod', 'talk', 'smile']
})
# Prepare the data
position = ('Time',)
interactions = cg.prepare_data(data, position, source='Source', target='Target', interaction='Interaction')
# Calculate weights (using the length of the interaction as weight)
weights = cg.calculate_weights(interactions, weight_func=lambda x: len(x))
# Aggregate weights
agg_weights = cg.agg_weights(weights, position)
# Create a temporal graph
tg = cg.TGraph(data=agg_weights, position=position, directed=True)
# Get the graph at time step 2
graph = tg.get_graph(time_point=(2,))
# Visualize the graph
fig, ax = plt.subplots()
cg.iplot(graph, target=ax)
plt.show()
2. Centrality Analysis
import ciga as cg
import pandas as pd
# ... (using the same 'data' and 'tg' from the previous example)
# Degree centrality
degree_centrality = cg.tgraph_degree(tg, weighted=True, normalized=True)
print("Degree Centrality:\n", degree_centrality)
# Betweenness centrality
betweenness_centrality = cg.tgraph_betweenness(tg, weighted=True, normalized=True)
print("Betweenness Centrality:\n", betweenness_centrality)
# Closeness centrality
closeness_centrality = cg.tgraph_closeness(tg, weighted=True, normalized=True)
print("Closeness Centrality:\n", closeness_centrality)
# Eigenvector centrality
eigenvector_centrality = cg.tgraph_eigenvector_centrality(tg, weighted=True)
print("Eigenvector Centrality:\n", eigenvector_centrality)
3. Community Detection
import ciga as cg
import pandas as pd
# ... (using the same 'data' and 'tg' from the previous example)
# Community detection using Leiden algorithm
communities = cg.tgraph_community_leiden(tg, weights='weight', resolution=1.0)
print("Communities:\n", communities)
4. Graph Properties
import ciga as cg
import pandas as pd
# ... (using the same 'data' and 'tg' from the previous example)
# Graph density over time
density = cg.tgraph_density(tg)
print("Density:\n", density)
# Graph transitivity over time
transitivity = cg.tgraph_transitivity_undirected(tg)
print("Transitivity:\n", transitivity)
5. Using a Custom Weight Function
import ciga as cg
import pandas as pd
from nltk.sentiment import SentimentIntensityAnalyzer
# Sample interaction data with text
data = pd.DataFrame({
'Time': [1, 1, 2, 2, 3],
'Source': ['Alice', 'Bob', 'Alice', 'Charlie', 'Bob'],
'Target': ['Bob', 'Alice', 'Charlie', 'Alice', 'Charlie'],
'Interaction': ['I like you', 'Thanks!', 'This is great', 'Hello', 'Nice to see you']
})
# Initialize sentiment analyzer
sid = SentimentIntensityAnalyzer()
# Custom weight function using sentiment analysis
def custom_weight_func(interaction):
return sid.polarity_scores(interaction)['compound'] # Using compound sentiment score as weight
# Prepare the data
position = ('Time',)
interactions = cg.prepare_data(data, position, source='Source', target='Target', interaction='Interaction')
# Calculate weights using the custom weight function
weights = cg.calculate_weights(interactions, weight_func=custom_weight_func)
# Aggregate weights
agg_weights = cg.agg_weights(weights, position)
# Create a temporal graph
tg = cg.TGraph(data=agg_weights, position=position, directed=True)
# Get the graph at time step 2
graph = tg.get_graph(time_point=(2,))
# Visualize the graph
fig, ax = plt.subplots()
cg.iplot(graph, target=ax)
plt.show()
6. Inferring Listeners with LLM
import ciga as cg
import pandas as pd
import anthropic
# Sample data with dialogue and scene descriptions
data = pd.DataFrame({
'Season': [1, 1, 1, 1, 1],
'Episode': [1, 1, 1, 2, 2],
'Scene': [1, 1, 2, 1, 1],
'Line': [1, 2, 3, 1, 2],
'Speaker': ['Alice', 'Bob', 'Charlie', 'Alice', 'Bob'],
'Dialogue': ['Hi Bob', 'Hello Alice', 'Hey everyone', 'Good morning', 'Morning Alice'],
'Action': ['Waive hand', 'Smile', '', 'Smile', 'Waive hand'],
'Scene_Description': ['In the room', 'In the room', 'In the room', 'In the room', 'In the room']
})
# Initialize Anthropic client (replace with your API key)
anthropic_client = anthropic.Anthropic(api_key="YOUR_API_KEY")
# Infer listeners
inferred_listeners = cg.infer_listeners(data=data,
position=('Season', 'Episode', 'Scene', 'Line'),
speaker='Speaker',
dialogue='Dialogue',
action='Action',
scene_description='Scene_Description',
client=anthropic_client,
mode='anthropic',
model='claude-3-5-haiku-latest',
max_tokens=200,
gap=0.5)
print("Inferred Listeners:\n", inferred_listeners)
7. Visualizing with Pyvis
import ciga as cg
import pandas as pd
# ... (using the same 'data' and 'tg' from the previous example)
# Get the graph at time step 2
graph = tg.get_graph(time_point=(2,))
# Visualize the graph using Pyvis
cg.pyviz(graph, output_file='interactive_graph.html')
Install
Install the latest version of CIGA:
$ pip install ciga
Install with visualization dependencies (for interactive plotting with pyviz):
$ pip install ciga[visualization]
Install with all optional dependencies:
$ pip install ciga[all]
Note: The pyviz function requires pyvis as an optional dependency. If you try to use pyviz without installing the visualization dependencies, you'll see a helpful error message with installation instructions.
To Do
- Add non-directed graph support
- Add closeness centrality
- Add Eigenvector centrality
- Add Leiden community detection
- Add forgetting simulation
- Add temporal visualization
- Add centrality visualizer (with visualization)
License
Released under the GNU General Public License v3.0.
Copyright (c) 2024 Media Comprehension Lab
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file ciga-0.0.9.tar.gz.
File metadata
- Download URL: ciga-0.0.9.tar.gz
- Upload date:
- Size: 51.8 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
45468aca798894fbc64f8e1a133f1481b80a67fb3f98cbe4db366b49c94a4e46
|
|
| MD5 |
a61c2db54793460194710dff7f0e74e2
|
|
| BLAKE2b-256 |
947472b4cbcf1fdb5893290b24a46c0eb9c72b736d846c7ea9ebefa1d1a2e581
|
File details
Details for the file ciga-0.0.9-py3-none-any.whl.
File metadata
- Download URL: ciga-0.0.9-py3-none-any.whl
- Upload date:
- Size: 57.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
df0930838f815a135bbf0b3ecf97473b964fb3544b95f0a042d65214460a8acc
|
|
| MD5 |
7a0534e2f6551f8a40bfc332af0b4c96
|
|
| BLAKE2b-256 |
431ffcf2a66c58f9018f80b5b104ea4f4fb2f99e68332bb4bd04281213589488
|