# Semantic Network stuff
class Entity:
def __init__(self,id):
self.id = id
self.mObjects = {}
self.mAgents = {}
def __str__(self):
return self.id
def objects(self,relation):
try: ans = self.mObjects[relation]
except: ans = []
if relation.transitive:
# if it's a transitive relation,
# pursue recursively
for i in tuple(ans):
ans = ans + i.objects(relation)
return ans
def agents(self,relation):
try: ans = self.mAgents[relation]
except: ans = []
if relation.inverse and relation.inverse.transitive:
# if its inverse is a transitive relation,
# pursue recursively
for i in tuple(ans):
ans = ans + i.agents(relation)
return ans
def storeObject(self,relation,object):
try:
lst = self.mObjects[relation]
if object not in lst: lst.append(object)
except:
self.mObjects[relation] = [object]
def storeAgent(self,relation,agent):
try:
lst = self.mAgents[relation]
if agent not in lst: lst.append(agent)
except:
self.mAgents[relation] = [agent]
# Get all the objects of a particular relation,
# where this (self) is the agent. These are cumulative.
# Note that there is no way currently for a subclass to
# override a base class; it can only extend it.
def getObjects(self,relation):
out = self.objects(relation)
# also check type-ancestors (base classes)
try: parents = self.mObjects[IS_A]
except: return out
for p in parents:
out = out + p.getObjects(relation)
return out
# Get all the agents of a particular relation,
# where this (self) is the object. These are cumulative.
def getAgents(self,relation):
out = self.agents(relation)
# also check type-ancestors (base classes)
try: parents = self.mObjects[IS_A]
except: return out
for p in parents:
out = out + p.getAgents(relation)
return out
class Relation:
def __init__(self, id, transitive=1, inverse=None ):
self.id = id
# a relation @ is transitive if
# A @ B and B @ C implies A @ C
self.transitive = transitive
if inverse:
self.inverse = inverse
inverse.inverse = self
else:
self.inverse = None
def __str__(self): return self.id
def __call__(self, agent, object=None):
# when used as a function, check to see whether
# this relation applies
obs = agent.getObjects(self)
if not object: return obs
if not obs or object not in obs: return 0
else: return 1
class Fact:
def __init__(self, agent, relation, object):
self.agent = agent
self.relation = relation
self.object = object
# stuff into dictionaries, for searching
agent.storeObject( relation, object )
object.storeAgent( relation, agent )
# deduce inverse relations as well
if relation.inverse:
object.storeObject( relation.inverse, agent )
agent.storeAgent( relation.inverse, object )
# declare global "is-a" relationship.
# other modules MUST properly use this, rather than
# define their own "is-a", since it has special meaning (inheritance).
IS_A = Relation("is-a",1)
EXAMPLE_OF = Relation("exampleOf", 1, IS_A)
# functions to allow outside access to these objects more easily:
def GetIsA(): return IS_A
def GetExampleOf(): return EXAMPLE_OF