New-space-openenv / plugins /codenames /word_interactions.py
Mooizz's picture
Upload folder using huggingface_hub
1070765 verified
"""Word interaction definitions for complex semantic relationships in Codenames.
Defines thematic clusters, polysemes, false friends, and semantic traps
to increase game complexity.
"""
from __future__ import annotations
from dataclasses import dataclass, field
from typing import Any
@dataclass
class WordRelation:
"""Represents a semantic relationship between words."""
word: str
related_words: list[str] = field(default_factory=list)
relation_type: str = "semantic" # semantic, thematic, homonym, false_friend, trap
domains: list[str] = field(default_factory=list) # e.g., ["finance", "nature"]
trap_level: int = 0 # 0=none, 1=mild, 2=moderate, 3=dangerous
@dataclass
class ThematicCluster:
"""A group of words sharing a hidden theme."""
theme: str
words: list[str]
secondary_themes: list[str] = field(default_factory=list)
@dataclass
class WordInteractions:
"""Container for all word interactions on a board."""
words: list[str]
relations: dict[str, WordRelation] = field(default_factory=dict)
clusters: list[ThematicCluster] = field(default_factory=list)
polysemes: list[str] = field(default_factory=list) # Words with multiple meanings
false_friends: list[tuple[str, str]] = field(default_factory=list) # Pairs that seem related but aren't
assassin_traps: list[str] = field(default_factory=list) # Words semantically close to assassin
def get_related_words(self, word: str) -> list[str]:
"""Get all words related to the given word."""
if word in self.relations:
return self.relations[word].related_words
return []
def get_trap_level(self, word: str) -> int:
"""Get the trap level for a word (how close to assassin)."""
if word in self.relations:
return self.relations[word].trap_level
return 0
def get_word_domains(self, word: str) -> list[str]:
"""Get the semantic domains for a word."""
if word in self.relations:
return self.relations[word].domains
return []
def to_dict(self) -> dict[str, Any]:
"""Serialize to dictionary for JSON output."""
return {
"words": self.words,
"relations": {
w: {
"related_words": r.related_words,
"relation_type": r.relation_type,
"domains": r.domains,
"trap_level": r.trap_level,
}
for w, r in self.relations.items()
},
"clusters": [
{"theme": c.theme, "words": c.words, "secondary_themes": c.secondary_themes}
for c in self.clusters
],
"polysemes": self.polysemes,
"false_friends": self.false_friends,
"assassin_traps": self.assassin_traps,
}
@classmethod
def from_dict(cls, data: dict[str, Any]) -> "WordInteractions":
"""Deserialize from dictionary."""
interactions = cls(words=data.get("words", []))
for word, rel_data in data.get("relations", {}).items():
interactions.relations[word] = WordRelation(
word=word,
related_words=rel_data.get("related_words", []),
relation_type=rel_data.get("relation_type", "semantic"),
domains=rel_data.get("domains", []),
trap_level=rel_data.get("trap_level", 0),
)
for cluster_data in data.get("clusters", []):
interactions.clusters.append(ThematicCluster(
theme=cluster_data.get("theme", ""),
words=cluster_data.get("words", []),
secondary_themes=cluster_data.get("secondary_themes", []),
))
interactions.polysemes = data.get("polysemes", [])
interactions.false_friends = [tuple(pair) for pair in data.get("false_friends", [])]
interactions.assassin_traps = data.get("assassin_traps", [])
return interactions