STGP problem

76 views
Skip to first unread message

Sergey Sosnin

unread,
Oct 1, 2014, 4:21:14 PM10/1/14
to deap-...@googlegroups.com
I have faced with a problem in my code:

pset = gp.PrimitiveSetTyped("main", [], str)
pset.addPrimitive(addRight,[str,str],str)
pset.addPrimitive(addLeft,[str,str],str)
pset.addPrimitive(branch,[str],str)
pset.addPrimitive(chain,[int],str)
pset.addPrimitive(makeBond,[str,str,int],str)
pset.addEphemeralConstant("atom",lambda : random.choice(atom_set),str)
pset.addEphemeralConstant("nums",lambda : random.randint(0,4),int)
expr = gp.genFull(pset, min_=1, max_=3)
tree = gp.PrimitiveTree(expr)
print tree

>>branch(branch(addLeft('As', 'C')))

The code above works correctly but only in rare starts. Usually, I have an exception:
Traceback (most recent call last):
  File "C:/Experiments/SMARTS/gp.py", line 81, in <module>
    expr = gp.genFull(pset, min_=1, max_=3)
  File "C:\Anaconda\lib\site-packages\deap\gp.py", line 516, in genFull
    return generate(pset, min_, max_, condition, type_)
  File "C:\Anaconda\lib\site-packages\deap\gp.py", line 600, in generate
    prim = random.choice(pset.primitives[type_])
  File "C:\Anaconda\lib\random.py", line 273, in choice
    return seq[int(self.random() * len(seq))]  # raises IndexError if seq is empty
IndexError: The gp.generate function tried to add a primitive of type '<type 'int'>', but there is none available.

If I modify code without 'int' types, all works fine:

pset = gp.PrimitiveSetTyped("main", [], str)
pset.addPrimitive(addRight,[str,str],str)
pset.addPrimitive(addLeft,[str,str],str)
pset.addPrimitive(branch,[str],str)
pset.addEphemeralConstant("atom",lambda : random.choice(atom_set),str)
expr = gp.genFull(pset, min_=1, max_=3)
tree = gp.PrimitiveTree(expr)
print tree

This code has never thrown an exception

Marc-André Gardner

unread,
Oct 1, 2014, 4:34:06 PM10/1/14
to deap-...@googlegroups.com
Hi Sergey,

Basically, the problem arises from the fact that you ask something impossible to DEAP. I've made an answer about this a while ago (https://groups.google.com/forum/#!searchin/deap-users/stgp/deap-users/wW5nZmAUI1U/vffCYmUGX1EJ), if you want to learn more, you can read it, but in summary, it all comes from the fact that you do not define a primitive that returns an integer, only a terminal. When DEAP absolutely needs a primitive with this return type to build a tree of the requested height, and there's none available, it throws this error.

If you want to convince yourself, try to build "by hand" a tree of height 4 which has "makeBond" as root.

So all in all, it comes from your problem definition. A quick & dirty way to fix that is to add a "dummy" primitive, which just takes an integer as argument and returns the same integer, thus allowing DEAP to create trees of any height. But it would definitely be better to try to define more adequatly your problem, so that issue never arises at the first place :-)

Do not hesitate if you have any remaining questions,

Marc-André
Reply all
Reply to author
Forward
0 new messages