def test_build_agent(self): prog = ''' Client agent: Agent is_duplicable = True Agent ''' #make_python(prog, debug=1) #DEBUG exec(compile_fargish(prog, saveto='tbu.gen.py'), globals()) #ShowActionList.start_logging() #ShowActionsChosen.start_logging() g = TestGraph(port_mates=port_mates) Client.is_duplicable = True # HACK client = g.add_node(Client) g.do_timestep() self.assertEqual(len(g), 2) agent = g.neighbor(client, port_label='agents') self.assertEqual(g.class_of(agent), Agent) self.assertTrue(g.has_hop(agent, 'behalf_of', client, 'agents')) # Once the agent is built, the client should not build another. g.do_timestep(num=5) self.assertEqual(len(g), 2) # Let's build another Client. It should get its own Agent. client2 = g.add_node(Client) g.do_timestep() self.assertEqual(len(g), 4) agent2 = g.neighbor(client2, port_label='agents') self.assertEqual(g.class_of(agent2), Agent) self.assertNotEqual(agent, agent2) g.do_timestep(num=5) self.assertEqual(len(g), 4)
def test_postamble(self): prog = ''' postamble { testPostamble } Blah ''' #make_python(prog, debug=True) #DEBUG exec(compile_fargish(prog), globals()) self.assertEqual(postamble_f(), Blah)
def test_node_with_arg(self): g = TestGraph() prog = ''' Number(n) Brick : Number''' #make_python(prog) #DEBUG exec(compile_fargish(prog), globals()) b = Brick(2) g.add_node(Brick(2)) got = g.nodes() expect = [Brick(n=2)] self.assertCountEqual(got, expect)
def test_autolink(self): #TODO Generate code for node_params, not auto_links prog = ''' target -- tags Number(n) Scout(target)''' #make_python(prog) #DEBUG exec(compile_fargish(prog), globals()) g = TestGraph(port_mates=port_mates) #nid = g.add_node(Number(3)) nid = g.add_node(Number, 3) #sid = g.add_node(Scout(nid)) sid = g.add_node(Scout, nid) self.assertTrue(g.has_hop(sid, 'target', nid, 'tags'))
def test_one_simple_node(self): g = TestGraph() prog = ''' SomeNode ''' exec(compile_fargish(prog), globals()) # The globals() argument makes exec put the newly defined classes # into our globals. Python does not provide a way (that works) for # exec to add classes to our local variables. This is unfortunate, # because each unit test leaves its class definitions in the global # space, potentially influencing unit tests that run later. g.add_node(SomeNode) got = g.nodes() expect = [SomeNode()] self.assertCountEqual(got, expect)
def test_multiply_inherit_param(self): prog = ''' tags -- taggees Tag(taggees) Number(value) #Count(value) : Tag, Number # You can't do this! You get two 'value' # params. The code generator can't coalesce the # 'value' params because some nodes need the # same param multiple times; e.g. ConsumeOperands # in brute.py takes two consume_operand params. Count : Tag, Number ''' exec(compile_fargish(prog), globals()) g = TestGraph(port_mates=port_mates) number = g.add_node(Number, 10) count = g.add_node(Count, taggees=[number], value=1) self.assertEqual(repr(count), 'Count(1)') self.assertTrue(g.has_hop(number, 'tags', count, 'taggees'))
import support prog = ''' tags -- taggees neighbors -- neighbors Tag(taggees) ZTag(value) : Tag SameZ, DiffZ : Tag Feature Corner, Line : Feature ''' #make_python(prog, debug=1) # Uncomment this to see generated code exec(compile_fargish(prog, saveto='necker.gen.py'), globals()) Feature.min_support_for = 1.0 class NeckerCubeGraph(TimeStepper, PortGraph): port_mates = port_mates def z0_of(g, nodeid): '''Returns id of ZTag on nodeid with value 0.''' return next(ztagid for ztagid in g.neighbors(nodeid, neighbor_class=ZTag) if g.value_of(ztagid) == 0 ) def z1_of(g, nodeid): '''Returns id of ZTag on nodeid with value 1.'''
Operator(operands, consumer) Plus, Times : Operator Minus(minuend, subtrahend) : Operator #AssessorScout(target) # #see winner := NodeWithValue(target.value, nodeclass=Number, tagclass=Avail) # #=> succeeded(winner, target) # see node := And(Or(NodeOfClass(Brick), NodeOfClass(Block)), # NodeWithTag(Avail), # Not(NodeWithTag(Assessment))) # => assess(node, target) ''' #make_python(prog, debug=1) exec(compile_fargish(prog, saveto='numbo5.gen.py'), globals()) Operator.is_duplicable = True #HACK Plus.expr_class = expr.Plus #HACK Plus.symbol = '+' #HACK Times.expr_class = expr.Times #HACK Times.symbol = '*' #HACK Numble = make_numble_class(Brick, Target, Want, Avail, Allowed, [Plus, Times, Minus]) ##### Hacks Number.is_duplicable = True
Diff(value) : Tag DiffIsWanted : Tag Number(value) Brick, Target, Block(source, consumer) : Number Operator(operands, result) Plus, Times : Operator Minus(minuend, subtrahend) : Operator Group(members) Workspace, Slipnet : Group Glom, LiveActiveChain : Group ''' #exec(compile_fargish(prog), globals()) exec(compile_fargish(prog, saveto='NumboGraph.gen.py'), globals()) Numble = make_numble_class(Brick, Target, Want, Avail, Allowed, [Plus, Times, Minus]) ##### Hacks Number.is_duplicable = True Operator.is_duplicable = True Brick.initial_activation = 1.0 Brick.min_support_for = 1.0 Target.initial_activation = 1.0 Target.min_support_for = 1.0
from StdGraph import Graph from codegen import make_python, compile_fargish from log import stop_all_logging prog = ''' postamble { gloms } glom -- glommees Glom Number(value) Brick, Target, Block : Number ''' exec(compile_fargish(prog, saveto='testGloms.gen.py'), globals()) class TestGraph(Graph): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.port_mates += port_mates class TestGloms(unittest.TestCase): def setUp(self): stop_all_logging() def test_glom_basics(self): g = TestGraph() b4 = g.add_node(Brick(4))
else see block := NodeWithTag(Block, Avail), \ block != target, \ block.value != target.value => Fail(block) SuccessScout(target) see winner := NodeWithValue(target.value, nodeclass=Number, tagclass=Avail) => succeeded(winner, target) ConsumeOperands(proposed_operator, consume_operand, consume_operand) see Not(Tagged(Done, this)), AllTagged(Avail, consume_operand(this)) => ConsumeOperandsAction() ''' #make_python(prog, debug=1) # Uncomment this to see generated code exec(compile_fargish(prog, saveto='brute.gen.py'), globals()) def fail(self, g, thisid): #HACK #print('BLOCKFAIL', g.nodestr(thisid)) for builder in g.neighbors(thisid, port_label='built_by'): g.datum(builder).fail(g, builder) Block.fail = fail Plus.expr_class = expr.Plus #HACK Plus.symbol = '+' #HACK Times.expr_class = expr.Times #HACK Times.symbol = '*' #HACK
see node := NodeOfClass((Brick, Block)) => build CouldBeOperand(node) ConsumeOperands OperandsScout(target) see p1 := NodeWithTag(Number, Avail), p2 := NodeWithTag(Number, Avail), op := NodeWithTag(Operator, Allowed) => build ConsumeOperands(op, p1, p2) else see block := NodeWithTag(Block, Avail), block != target => Fail(block) ''' make_python(prog, debug=1) exec(compile_fargish(prog), globals()) Numble = make_numble_class(Brick, Target, Want, Avail, Allowed, [Plus, Times, Minus]) ##### Hacks tag_port_label = 'taggees' taggee_port_label = 'tags' @classmethod def cls_add_tag(cls, g, taggees): # HACK taggees = list(as_iter(taggees)) taggee_containers = intersection( *[g.member_of(ee) for ee in as_iter(taggees)])