Commit 1a1b931c authored by Savva Golubitsky's avatar Savva Golubitsky

working on subgraphs

parent 1cf3938f
...@@ -24,7 +24,7 @@ class Func(): ...@@ -24,7 +24,7 @@ class Func():
elif dummy: elif dummy:
self.func = lambda data: data self.func = lambda data: data
else: else:
print(module, name, "loading") # print(module, name, "loading")
self.func = getattr(imp.import_module(module), name) self.func = getattr(imp.import_module(module), name)
def __str__(self): def __str__(self):
...@@ -100,6 +100,7 @@ class Graph: ...@@ -100,6 +100,7 @@ class Graph:
if '__EXCEPTION__' in data: if '__EXCEPTION__' in data:
return False return False
# cur_state, implicit_parallelization_info = morph(data) # cur_state, implicit_parallelization_info = morph(data)
print(cur_state.name, transfer_f)
cur_state = transfer_f(data) cur_state = transfer_f(data)
# print(morph) # print(morph)
if '__EXCEPTION__' in data: if '__EXCEPTION__' in data:
...@@ -149,7 +150,6 @@ class State: ...@@ -149,7 +150,6 @@ class State:
def idle_run(self, idle_run_type, branching_states_history): def idle_run(self, idle_run_type, branching_states_history):
def __sort_by_order(tr): def __sort_by_order(tr):
# print(tr.edge.order)
return tr.edge.order return tr.edge.order
self.transfers.sort(key = __sort_by_order) self.transfers.sort(key = __sort_by_order)
print(self.name) print(self.name)
...@@ -195,12 +195,12 @@ class State: ...@@ -195,12 +195,12 @@ class State:
graph.term_state.transfers = self.transfers graph.term_state.transfers = self.transfers
def run(self, data, implicit_parallelization_info=None): def run(self, data, implicit_parallelization_info=None):
print('STATE {}, just entered, implicit_parallelization_info: {}'.format(self.name, implicit_parallelization_info)) print('STATE {}\n\tjust entered, implicit_parallelization_info: {}'.format(self.name, implicit_parallelization_info))
if self._proxy_state is not None: if self._proxy_state is not None:
return self._proxy_state.run(data, implicit_parallelization_info) return self._proxy_state.run(data, implicit_parallelization_info)
self._activate_input_edge(implicit_parallelization_info) self._activate_input_edge(implicit_parallelization_info)
#self.activated_input_edges_number += 1 #self.activated_input_edges_number += 1
print('STATE {}, required input: {}, active: {}, looped: {}'.format(self.name, self.input_edges_number, self.activated_input_edges_number, self.looped_edges_number)) print('\trequired input: {}, active: {}, looped: {}'.format(self.input_edges_number, self.activated_input_edges_number, self.looped_edges_number))
# print('qwer') # print('qwer')
if not self._ready_to_transfer(implicit_parallelization_info): if not self._ready_to_transfer(implicit_parallelization_info):
return None, None # it means that this state waits for some incoming edges (it is a point of collision of several edges) return None, None # it means that this state waits for some incoming edges (it is a point of collision of several edges)
...@@ -215,12 +215,13 @@ class State: ...@@ -215,12 +215,13 @@ class State:
for transfer in self.transfers: for transfer in self.transfers:
predicate_values.append(transfer.edge.predicate(data, dynamic_keys_mapping)) predicate_values.append(transfer.edge.predicate(data, dynamic_keys_mapping))
selected_edges = self.selector.func(predicate_values) selected_edges = self.selector.func(predicate_values)
print(selected_edges)
if not selected_edges: if not selected_edges:
raise GraphUnexpectedTermination( raise GraphUnexpectedTermination(
'State {}: Predicate values {} do not conform selection policy'.format(self.name, predicate_values)) 'State {}: Predicate values {} do not conform selection policy'.format(self.name, predicate_values))
selected_transfers = [self.transfers[i] for i, _ in enumerate(selected_edges) if selected_edges[i]==True] selected_transfers = [self.transfers[i] for i, _ in enumerate(selected_edges) if selected_edges[i]==True]
print( selected_transfers) for transf in selected_transfers:
if not transf.edge.predicate(data, dynamic_keys_mapping):
raise Exception("\tERROR: predicate {} returns False running from STATE {}".format(transf.edge.pred_name, self.name))
return self.parallelization_policy.make_transfer_func(selected_transfers, return self.parallelization_policy.make_transfer_func(selected_transfers,
array_keys_mapping=self.array_keys_mapping, array_keys_mapping=self.array_keys_mapping,
implicit_parallelization_info=implicit_parallelization_info,), \ implicit_parallelization_info=implicit_parallelization_info,), \
...@@ -283,7 +284,6 @@ class SerialParallelizationPolicy: ...@@ -283,7 +284,6 @@ class SerialParallelizationPolicy:
def make_transfer_func(self, morphisms, array_keys_mapping=None, implicit_parallelization_info=None): def make_transfer_func(self, morphisms, array_keys_mapping=None, implicit_parallelization_info=None):
def _morph(data): def _morph(data):
print("\tmorphisms:",len(morphisms))
if array_keys_mapping is None: if array_keys_mapping is None:
dynamic_keys_mapping = build_dynamic_keys_mapping(implicit_parallelization_info) dynamic_keys_mapping = build_dynamic_keys_mapping(implicit_parallelization_info)
next_morphs = [partial(morphism.transfer, dynamic_keys_mapping=dynamic_keys_mapping) for morphism in morphisms] next_morphs = [partial(morphism.transfer, dynamic_keys_mapping=dynamic_keys_mapping) for morphism in morphisms]
......
...@@ -29,49 +29,50 @@ class Params(): ...@@ -29,49 +29,50 @@ class Params():
stri += s+": {}, ".format(getattr(self, s)) stri += s+": {}, ".format(getattr(self, s))
return stri return stri
entities = {} # entities = {}
class GraphFactory(): class GraphFactory():
__slots__ = ( __slots__ = (
'name',
'states', 'states',
'graph', 'graph',
'issub',
'tocpp', 'tocpp',
'entities' 'entities'
) )
def __init__(self, tocpp=False): def __init__(self, tocpp=False):
self.states = {} self.states = {}
self.entities = {}
self.tocpp = tocpp self.tocpp = tocpp
self.name = None
self.issub = False
def add_state(self, statename): def add_state(self, statename):
if statename not in self.states: if statename not in self.states:
newstate = State(statename) self.states[statename] = State(statename)
self.states[statename] = newstate
def _create_morphism(self, morphname=None): def _create_morphism(self, morphname=None):
if morphname is None: if morphname is None:
return Func(), Func() return Func(), Func()
pred_f, func_f = Func(), Func() pred_f, func_f = Func(), Func()
morph = entities[morphname] morph = self.entities[morphname]
# print(morph) # print(morph)
for m in morph.__slots__: for m in morph.__slots__:
if getattr(morph,m) != None: if getattr(morph,m) != None:
if m!="predicate" and m!="function": if m!="predicate" and m!="function":
print("ERROR: Morphisms could not have any params exept predicate and function!\n{}".format(morphname)) raise Exception("ERROR: Morphisms could not have any params exept predicate and function!\n{}".format(morphname))
exit(0)
if m=="predicate": if m=="predicate":
if getattr(morph,m) not in entities: if getattr(morph,m) not in self.entities:
print("\tERROR: Predicate {} is not defined!".format(getattr(morph, m))) raise Exception("\tERROR: Predicate {} is not defined!".format(getattr(morph, m)))
exit(0) pred = self.entities[getattr(morph, m)]
pred = entities[getattr(morph, m)]
if self.tocpp: if self.tocpp:
pred_f = Func(pred.module, pred.entry_func, dummy=True) pred_f = Func(pred.module, pred.entry_func, dummy=True)
else: else:
pred_f = Func(pred.module, pred.entry_func) pred_f = Func(pred.module, pred.entry_func)
if m=="function": if m=="function":
if getattr(morph,m) not in entities: if getattr(morph,m) not in self.entities:
print("\tERROR: Function: {} is not defined!".format(getattr(morph, m))) raise Exception("\tERROR: Function: {} is not defined!".format(getattr(morph, m)))
exit(0) fu = self.entities[getattr(morph, m)]
fu = entities[getattr(morph, m)]
if self.tocpp: if self.tocpp:
func_f = Func(fu.module, fu.entry_func, dummy=True) func_f = Func(fu.module, fu.entry_func, dummy=True)
else: else:
...@@ -86,26 +87,36 @@ class GraphFactory(): ...@@ -86,26 +87,36 @@ class GraphFactory():
def build(self): def build(self):
for s in self.states: for s in self.states:
if s in entities and entities[s].selector is not None: if s in self.entities and self.entities[s].selector is not None:
if self.tocpp: if self.tocpp:
self.states[s].selector = Selector(len(self.states[s].transfers), entities[s].module, entities[s].entry_func, dummy=True) self.states[s].selector = Selector(len(self.states[s].transfers), self.entities[s].module, self.entities[s].entry_func, dummy=True)
else: else:
self.states[s].selector = Selector(len(self.states[s].transfers), entities[s].module, entities[s].entry_func) self.states[s].selector = Selector(len(self.states[s].transfers), self.entities[s].module, self.entities[s].entry_func)
else: else:
self.states[s].selector = Selector(len(self.states[s].transfers)) self.states[s].selector = Selector(len(self.states[s].transfers))
self.graph = Graph(self.states["__BEGIN__"], self.states["__END__"]) if s in self.entities and self.entities[s].subgraph is not None:
subgr = Parser(subgraph=True).parse_file(self.entities[s].subgraph)
# print(self.states[s].transfers)
self.states[s].replace_with_graph(subgr)
print(subgr.term_state.transfers)
if self.issub:
self.graph = Graph(self.states[self.name+"_"+"__BEGIN__"], self.states[self.name+"_"+"__END__"])
else:
self.graph = Graph(self.states["__BEGIN__"], self.states["__END__"])
self.graph.init_graph() self.graph.init_graph()
return self.graph return self.graph
class Parser(): class Parser():
__slots__ = ( __slots__ = (
'entities', 'entities',
'fact' 'fact',
'issub'
) )
def __init__(self, tocpp=False): def __init__(self, tocpp=False, subgraph=False):
self.entities = {}
self.fact = GraphFactory(tocpp=tocpp) self.fact = GraphFactory(tocpp=tocpp)
self.fact.issub = subgraph
self.issub = subgraph
def _check_brackets(self, rawfile): def _check_brackets(self, rawfile):
br = 0 br = 0
...@@ -126,8 +137,7 @@ class Parser(): ...@@ -126,8 +137,7 @@ class Parser():
elif char =="\"": elif char =="\"":
qu+=1 qu+=1
if br!=0 or qu%2!=0: if br!=0 or qu%2!=0:
print("Brackets or quotes do not match! Check your file") raise Exception("Brackets or quotes do not match! Check your file")
exit(-1)
def _split_multiple(self,param): def _split_multiple(self,param):
vals = {} vals = {}
...@@ -141,13 +151,11 @@ class Parser(): ...@@ -141,13 +151,11 @@ class Parser():
if l==0: if l==0:
l=len(vals[sl]) l=len(vals[sl])
elif l!=len(vals[sl]): elif l!=len(vals[sl]):
print("\tERROR: Number of multiple params do not match", l) raise Exception("\tERROR: Number of multiple params do not match", l)
exit(-1)
res = [copy.copy(param) for i in range(l)] res = [copy.copy(param) for i in range(l)]
for sl in vals: for sl in vals:
for i, _ in enumerate(res): for i, _ in enumerate(res):
setattr(res[i], sl, vals[sl][i]) setattr(res[i], sl, vals[sl][i])
print("SPLIT:",res[0])
return res return res
#Props is line "[proFp=smth, ...]" #Props is line "[proFp=smth, ...]"
...@@ -158,6 +166,10 @@ class Parser(): ...@@ -158,6 +166,10 @@ class Parser():
mchs = [m for m in re.finditer(r'\((\w+,)*\w+\)', props)] mchs = [m for m in re.finditer(r'\((\w+,)*\w+\)', props)]
for m in mchs: for m in mchs:
props=props[:m.span()[0]]+(props[m.span()[0]:m.span()[1]]).replace(',','\0')+props[m.span()[1]:] props=props[:m.span()[0]]+(props[m.span()[0]:m.span()[1]]).replace(',','\0')+props[m.span()[1]:]
if '\"' in props:
mchs = [m for m in re.finditer(r'\".*\"', props)]
for m in mchs:
props=props[:m.span()[0]]+(props[m.span()[0]+1:m.span()[1]-1]).replace('\0',' ')+props[m.span()[1]:]
props = props.replace("(","") props = props.replace("(","")
props = props.replace(")","") props = props.replace(")","")
rs =props.split(r",") #.split(r", ") rs =props.split(r",") #.split(r", ")
...@@ -179,16 +191,19 @@ class Parser(): ...@@ -179,16 +191,19 @@ class Parser():
spl = list(filter(lambda x: x!="[" and x!="]" and x!="", spl)) spl = list(filter(lambda x: x!="[" and x!="]" and x!="", spl))
left = spl[0].split(",") left = spl[0].split(",")
right = spl[2].split(",") right = spl[2].split(",")
if self.issub:
for i in range(len(left)):
left[i] = self.fact.name + "_" + left[i]
for i in range(len(right)):
right[i] = self.fact.name + "_" + right[i]
if (len(left)>1) and (len(right)>1): if (len(left)>1) and (len(right)>1):
print("ERROR:Ambigious multiple connection in line:\n\t{}".format(raw)) raise Exception("ERROR:Ambigious multiple connection in line:\n\t{}".format(raw))
exit()
# many to one conection # many to one conection
elif len(left)>1: elif len(left)>1:
p = self._param_from_props(spl[3]) p = self._param_from_props(spl[3])
morphs = self._split_multiple(p) morphs = self._split_multiple(p)
if len(morphs)!=len(left): if len(morphs)!=len(left):
print("\tERROR:Count of edges do not match to count of states in many to one connection!\n\t\t{}".format(raw)) raise Exception("\tERROR:Count of edges do not match to count of states in many to one connection!\n\t\t{}".format(raw))
exit()
self.fact.add_state(right[0]) self.fact.add_state(right[0])
for i, st in enumerate(left): for i, st in enumerate(left):
self.fact.add_state(st) self.fact.add_state(st)
...@@ -200,8 +215,7 @@ class Parser(): ...@@ -200,8 +215,7 @@ class Parser():
morphs = self._split_multiple(p) morphs = self._split_multiple(p)
print("MORPH", morphs[0]) print("MORPH", morphs[0])
if len(morphs)!=len(right): if len(morphs)!=len(right):
print("\tERROR:Count of edges do not match to count of states in one to many connection!\n\t\t{}".format(raw)) raise Exception("\tERROR:Count of edges do not match to count of states in one to many connection!\n\t\t{}".format(raw))
exit()
for i, st in enumerate(right): for i, st in enumerate(right):
self.fact.add_state(st) self.fact.add_state(st)
self.fact.add_connection(left[0], st, morphs[i].morphism, morphs[i].order) self.fact.add_connection(left[0], st, morphs[i].morphism, morphs[i].order)
...@@ -224,7 +238,7 @@ class Parser(): ...@@ -224,7 +238,7 @@ class Parser():
for m in comments: for m in comments:
dot=dot[:m.span()[0]]+(dot[m.span()[0]:m.span()[1]]).replace(' ','\0')+dot[m.span()[1]:] dot=dot[:m.span()[0]]+(dot[m.span()[0]:m.span()[1]]).replace(' ','\0')+dot[m.span()[1]:]
dot = re.sub(r"[ \t\r]", "", dot) #deleting all spaces dot = re.sub(r"[ \t\r]", "", dot) #deleting all spaces
dot = re.sub(r"((digraph\w+\n?)|}|{)", "", dot) dot = re.sub(r"((digraph)|}|{)", "", dot)
dot = re.sub(r"\/\/.*", "", dot) dot = re.sub(r"\/\/.*", "", dot)
dot = re.sub(r"^\n$", "", dot) dot = re.sub(r"^\n$", "", dot)
#print("Checking graph...") #print("Checking graph...")
...@@ -237,6 +251,8 @@ class Parser(): ...@@ -237,6 +251,8 @@ class Parser():
#dot = re.sub(r"//*$", "", dot) #dot = re.sub(r"//*$", "", dot)
dotlines = dot.splitlines() dotlines = dot.splitlines()
dotlines = list(filter(None, dotlines)) dotlines = list(filter(None, dotlines))
self.fact.name = dotlines[0]
dotlines = dotlines[1:]
# ent_re - regular expr for edges, states, functions properties # ent_re - regular expr for edges, states, functions properties
ent_re = re.compile(r"^\w+\[.*\]$") ent_re = re.compile(r"^\w+\[.*\]$")
# top_re - regular expr for topology properties, most time consuming one # top_re - regular expr for topology properties, most time consuming one
...@@ -245,9 +261,8 @@ class Parser(): ...@@ -245,9 +261,8 @@ class Parser():
for i, ln in enumerate(dotlines): for i, ln in enumerate(dotlines):
if ent_re.match(ln): if ent_re.match(ln):
name, parm = self._param_from_entln(ln) name, parm = self._param_from_entln(ln)
entities[name] = parm self.fact.entities[name] = parm
elif top_re.match(ln): elif top_re.match(ln):
self._topology(ln) self._topology(ln)
self.entities = entities
return self.fact.build() return self.fact.build()
...@@ -15,10 +15,10 @@ def decrement_a_edge(data): ...@@ -15,10 +15,10 @@ def decrement_a_edge(data):
data['a'] -= 1 data['a'] -= 1
def nonzero_predicate(data): def nonzero_predicate(data):
return True if data['a'] != 0 else False return data['a'] != 0
def positiveness_predicate(data): def positiveness_predicate(data):
return True if data['a'] > 0 else False return data['a'] > 0
def nonpositiveness_predicate(data): def nonpositiveness_predicate(data):
return True if data['a'] <= 0 else False return data['a'] <= 0
\ No newline at end of file \ No newline at end of file
digraph ADD {
FUNC [module=test_funcs.simplest, entry_func=increment_a_edge]
PRED [module=test_funcs.simplest, entry_func=positiveness_predicate]
MORPH [predicate=PRED, function=FUNC]
__BEGIN__ -> __END__ [morphism = MORPH]
}
\ No newline at end of file
digraph SIMPLEST { digraph SIMPLEST {
FUNC [module=test_funcs.simplest, entry_func=increment_a_edge] FUNC [module=test_funcs.simplest, entry_func=increment_a_edge]
PRED [module=test_funcs.simplest, entry_func=nonzero_predicate] PRED [module=test_funcs.simplest, entry_func=positiveness_predicate]
MORPH [predicate=PRED, function=FUNC] MORPH [predicate=PRED, function=FUNC]
__BEGIN__ -> ST1 [morphism = MORPH] ST1 [subgraph=./tests/parser_test/add.adot]
__BEGIN__ -> ST1
ST1 -> ST2 [morphism=MORPH] ST1 -> ST2 [morphism=MORPH]
ST2 -> __END__ [morphism=MORPH] ST2 -> __END__ [morphism=MORPH]
} }
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment