Python - Help on genetic algorithm error - python

I've been trying to create a genetic algorithm in python but i either get:
<bound method Environment.bestsol of <__main__.Environment instance
at 0x10a5d4ab8>>
or it doesn't print. I've tried to rearrange the functions, and call the function directly, but it still does not output anything. I seem to be having trouble with something relating to the function bestsol().
import random
import sys
from operator import attrgetter
input = 1
target = 5.5
class Individual:
def __init__(self, constant):
self.fitness = getfitness()
self.constant = constant
def getconstant():
return self.constant
def getresult():
return self.constant * input
def getfitness():
return 10 - abs(target - self.getresult())
def mutate():
if(random.random() > .05):
self.constant + random.random()
def offspring(partner):
return Individual(((self.getconstant() + partner.getconstant())/2))
class Generation(list):
def __init__(self, gensize, fitsize, startinglist=[]):
self.extend(startinglist)
self.bredoff = []
self.gensize = gensize
self.fitsize = fitsize
self.make()
def make():
self = [Individual(random.randint(-10,10)) for x in xrange((self.gensize-len(self)))]
def getfittest():
return heapq.nlargest(self.fitsize,self,key=attrgetter('fitness'))
def getbredoffspring():
for i in self.getfittest():
bredoff.append(i.offspring(self.getfittest[random.randint(0,len(self.getfittest()))]))
return bredoff
class Environment():
def __init__(self, maxgens):
self.l = []
self.b = []
self.maxgens = maxgens
def create():
l = Generation(100,20)
for i in maxgens:
b = l.getbredoffspring()
l = Generation(100,20,b)
def bestsol():
print("e")
print max(l,key=attrgetter('fitness')).fitness()
def main():
sol = Environment(2)
print sol.bestsol
if __name__ == '__main__':
main()
With me being new to python i can't understand even after searching the internet as best i could. Any help will be appreciated.

bestsol is a class method, so when you call it you should use brackets: sol.bestsol() (otherwise, you're print the method object: <bound method Environment.bestsol ...).
Second, when you define a class-method you should declare self as an argument:
def bestsol(self): # <-- here
print("e")
print max(l,key=attrgetter('fitness')).fitness()
Third, when you declare a class that doesn't extend any other class - you should either declare that it inherits from object (old way):
class Environment(object):
or, no brackets at all (new way)
class Environment:
Forth, when you create a class member, say l (you really should use better names btw), whenever you want to use it you should use the self annotation: self.l. If you'll use l it will create a local variable inside the method - and that's probably not what you intended.
There are other problems with the code but I'll let you struggle with it a bit so you can learn :)

Related

Python Fix Dependancy Cycle

I'm working on a game using python.
The AI in the game uses variables that the player has, and vice versa.
For an example:
class Player():
def __init__(self, canvas...):
self.id = canvas.create_rectangle(...)
...
def touching_AI(self):
aipos = canvas.coords(AI object)
pos = canvas.coords(self.id)
...
#the function above checks if the player is touching the AI if it
#is, then call other functions
this = player(canvas...)
class AI():
def __init__(self, canvas...):
self.id = canvas.create_rectangle(...)
def chase_player(self):
playerpos = canvas.coords(this.id)
pos = canvas.coords(self.id)
...
# a lot of code that isn't important
Obviously, Python says that the AI object in the player class isn't defined. Both classes depend on the other to work. However, one isn't defined yet, so if I put one before the other, it returns an error. While there is probably a workaround for these two functions only, there are more functions that I didn't mention.
In summary, is there a way (pythonic or non-pythonic) to use and/or define an object before it is created (i.e even making more files)?
you do not
instead use arguments
class Player():
def __init__(self, canvas...):
self.id = canvas.create_rectangle(...)
...
def touching(self,other):
aipos = canvas.coords(other.object)
pos = canvas.coords(self.id)
...
#the function above checks if the player is touching the AI if it
#is, then call other functions
class AI():
def __init__(self, canvas...):
self.id = canvas.create_rectangle(...)
def chase(self,player):
playerpos = canvas.coords(player.id)
pos = canvas.coords(self.id)
then
player = Player(canvas...)
ai = AI(...)
ai.chase(player)
player.touching(ai)
but even better is to define a base object type that defines your interface
class BaseGameOb:
position = [0,0]
def distance(self,other):
return distance(self.position,other.position)
class BaseGameMob(BaseGameOb):
def chase(self,something):
self.target = something
def touching(self,other):
return True or False
then all your things inherit from this
class Player(BaseGameMob):
... things specific to Player
class AI(BaseGameMob):
... things specific to AI
class Rat(AI):
... things specific to a Rat type AI
You do not have a dependency cycle problem. But, you have the following problem,
You are trying it use an AI object, but you did not create the object anywhere. It needs to look like,
foo = AI() #creating the object
bar(foo) #using the object
The syntax is wrong around canvas.coords(AI object).
The way to call a function is foo(obj) without the type.
When defining a function you can optionally mention the type like def foo(bar : 'AI'):
The proof you can depend classes on each other, https://pyfiddle.io/fiddle/b75f2de0-2956-472d-abcf-75a627e77204/
You can initialize one without specifying the type and assign it in afterwards. Python kind of pretends everyone are grown-ups so..
e.g.:
class A:
def __init__(self, val):
self.val = val
self.b = None
class B:
def __init__(self, a_val):
self.a = A(a_val)
a_val = 1
b = B(1)
a = b.a
a.b = b

How to get one value from a method in class without recalculating?

I am wondering if I can get a value from a method which does not belong to object, and use it in another method under the same class.
Here is a sample code:
class Additon:
def __init__(self,number):
self.number=number
def arithmetic(self,k):
newnumber1=self.number+k
newnumber2 = self.number-k
return [newnumber1,newnumber2]
def add(self):
a=self.arithmetic(1)
return a[0]
def minus(self):
#get new number2
I would like to get newnumber2 in minus method without calling arithmetic again. This is just a sample code for my programming assignment, the result does not matter. I would like to know the way of doing this.
class Additon:
def __init__(self,number):
self.number=number
def arithmetic(self,k):
newnumber1=self.number+k
self.newnumber2 = self.number-k
return [newnumber1,newnumber2]
def add(self):
a=self.arithmetic(1)
return a[0]
def minus(self):
return self.newnumber2

Polymorphism and Overriding in Python

I have two classes: A and B. I would like to build a class C which is able to overrides some common methods of A and B.
The methods which I would like to override they should be able to call the method of the base class.
In practice I would like to collect some statistics about class A and B, but being transparent to the rest of my code. Now, A and B have some methods in common (obviously implemented in a different way). I would like to have a class C which shares the interface of A and B, and simoultaneously do some other operations (i.e. measure the run time of some shared methods).
I can make this example:
import time
class A:
def __init__(self):
pass
def common_method(self):
return "A"
class B:
def __init__(self):
pass
def common_method(self):
return "B"
class C:
def __init__(self, my_obj):
self.my_obj
self.time_avg = 0
self.alpha = 0.1
pass
def common_method(self):
start = time.time()
ret = self.my_obj.common_method()
stop = time.time()
self.time_avg = (1. - self.alpha) * self.time_avg + self.alpha * (stop - start)
return ret
I hope that from this example is clear that A and B inheriting from C is not working.
However, this method unfortunately require me to redefine all the methods of classes A and B... Which is tedious and dirty!
What is the proper way to implement this situation in python? And how it is called the design pattern (I am almost sure that there is but I cannot recall).
Thanks in advance.
You could solve this with composition instead of polymorphism, meaning that a C object will hold either a A object or a B one:
class C:
def __init__(self, obj):
self._obj = obj
def common_method(self):
return self._obj.common_method()
You can then use it:
>>> ca = C(A())
>>> cb = C(B())
>>> ca.common_method()
'A'
>>> cb.common_method()
'B'
Beware: if you pass an object that does not declare a common_method method, you will get an AttributeError

Dynamically generate method from string?

I have a dict of different types for which I want to add a simple getter based on the name of the actual parameter.
For example, for three storage parameters, let's say:
self.storage = {'total':100,'used':88,'free':1}
I am looking now for a way (if possible?) to generate a function on the fly with some meta-programming magic.
Instead of
class spaceObj(object):
def getSize(what='total'):
return storage[what]
or hard coding
#property
def getSizeTotal():
return storage['total']
but
class spaceObj(object):
# manipulting the object's index and magic
#property
def getSize:
return ???
so that calling mySpaceObj.getSizeFree would be derived - with getSize only defined once in the object and related functions derived from it by manipulating the objects function list.
Is something like that possible?
While certainly possible to get an unknown attribute from a class as a property, this is not a pythonic approach (__getattr__ magic methods are rather rubyist)
class spaceObj(object):
storage = None
def __init__(self): # this is for testing only
self.storage = {'total':100,'used':88,'free':1}
def __getattr__(self, item):
if item[:7] == 'getSize': # check if an undefined attribute starts with this
return self.getSize(item[7:])
def getSize(self, what='total'):
return self.storage[what.lower()]
print (spaceObj().getSizeTotal) # 100
You can put the values into the object as properties:
class SpaceObj(object):
def __init__(self, **kwargs):
self.__dict__.update(kwargs)
storage = {'total':100,'used':88,'free':1}
o = SpaceObj(**storage)
print o.total
or
o = SpaceObj(total=100, used=88, free=1)
print o.total
or using __getattr__:
class SpaceObj(object):
def __init__(self, **kwargs):
self.storage = kwargs
def __getattr__(self,name):
return self.storage[name]
o = SpaceObj(total=100, used=88, free=1)
print o.total
The latter approach takes a bit more code but it's more safe; if you have a method foo and someone create the instance with SpaceObj(foo=1), then the method will be overwritten with the first approach.
>>> import new
>>> funcstr = "def wat(): print \"wat\";return;"
>>> funcbin = compile(funcstr,'','exec')
>>> ns = {}
>>> exec funcbin in ns
>>> watfunction = new.function(ns["wat"].func_code,globals(),"wat")
>>> globals()["wat"]=watfunction
>>> wat()
wat

python lazy variables? or, delayed expensive computation

I have a set of arrays that are very large and expensive to compute, and not all will necessarily be needed by my code on any given run. I would like to make their declaration optional, but ideally without having to rewrite my whole code.
Example of how it is now:
x = function_that_generates_huge_array_slowly(0)
y = function_that_generates_huge_array_slowly(1)
Example of what I'd like to do:
x = lambda: function_that_generates_huge_array_slowly(0)
y = lambda: function_that_generates_huge_array_slowly(1)
z = x * 5 # this doesn't work because lambda is a function
# is there something that would make this line behave like
# z = x() * 5?
g = x * 6
While using lambda as above achieves one of the desired effects - computation of the array is delayed until it is needed - if you use the variable "x" more than once, it has to be computed each time. I'd like to compute it only once.
EDIT:
After some additional searching, it looks like it is possible to do what I want (approximately) with "lazy" attributes in a class (e.g. http://code.activestate.com/recipes/131495-lazy-attributes/). I don't suppose there's any way to do something similar without making a separate class?
EDIT2: I'm trying to implement some of the solutions, but I'm running in to an issue because I don't understand the difference between:
class sample(object):
def __init__(self):
class one(object):
def __get__(self, obj, type=None):
print "computing ..."
obj.one = 1
return 1
self.one = one()
and
class sample(object):
class one(object):
def __get__(self, obj, type=None):
print "computing ... "
obj.one = 1
return 1
one = one()
I think some variation on these is what I'm looking for, since the expensive variables are intended to be part of a class.
The first half of your problem (reusing the value) is easily solved:
class LazyWrapper(object):
def __init__(self, func):
self.func = func
self.value = None
def __call__(self):
if self.value is None:
self.value = self.func()
return self.value
lazy_wrapper = LazyWrapper(lambda: function_that_generates_huge_array_slowly(0))
But you still have to use it as lazy_wrapper() not lazy_wrapper.
If you're going to be accessing some of the variables many times, it may be faster to use:
class LazyWrapper(object):
def __init__(self, func):
self.func = func
def __call__(self):
try:
return self.value
except AttributeError:
self.value = self.func()
return self.value
Which will make the first call slower and subsequent uses faster.
Edit: I see you found a similar solution that requires you to use attributes on a class. Either way requires you rewrite every lazy variable access, so just pick whichever you like.
Edit 2: You can also do:
class YourClass(object)
def __init__(self, func):
self.func = func
#property
def x(self):
try:
return self.value
except AttributeError:
self.value = self.func()
return self.value
If you want to access x as an instance attribute. No additional class is needed. If you don't want to change the class signature (by making it require func), you can hard code the function call into the property.
Writing a class is more robust, but optimizing for simplicity (which I think you are asking for), I came up with the following solution:
cache = {}
def expensive_calc(factor):
print 'calculating...'
return [1, 2, 3] * factor
def lookup(name):
return ( cache[name] if name in cache
else cache.setdefault(name, expensive_calc(2)) )
print 'run one'
print lookup('x') * 2
print 'run two'
print lookup('x') * 2
Python 3.2 and greater implement an LRU algorithm in the functools module to handle simple cases of caching/memoization:
import functools
#functools.lru_cache(maxsize=128) #cache at most 128 items
def f(x):
print("I'm being called with %r" % x)
return x + 1
z = f(9) + f(9)**2
You can't make a simple name, like x, to really evaluate lazily. A name is just an entry in a hash table (e.g. in that which locals() or globals() return). Unless you patch access methods of these system tables, you cannot attach execution of your code to simple name resolution.
But you can wrap functions in caching wrappers in different ways.
This is an OO way:
class CachedSlowCalculation(object):
cache = {} # our results
def __init__(self, func):
self.func = func
def __call__(self, param):
already_known = self.cache.get(param, None)
if already_known:
return already_known
value = self.func(param)
self.cache[param] = value
return value
calc = CachedSlowCalculation(function_that_generates_huge_array_slowly)
z = calc(1) + calc(1)**2 # only calculates things once
This is a classless way:
def cached(func):
func.__cache = {} # we can attach attrs to objects, functions are objects
def wrapped(param):
cache = func.__cache
already_known = cache.get(param, None)
if already_known:
return already_known
value = func(param)
cache[param] = value
return value
return wrapped
#cached
def f(x):
print "I'm being called with %r" % x
return x + 1
z = f(9) + f(9)**2 # see f called only once
In real world you'll add some logic to keep the cache to a reasonable size, possibly using a LRU algorithm.
To me, it seems that the proper solution for your problem is subclassing a dict and using it.
class LazyDict(dict):
def __init__(self, lazy_variables):
self.lazy_vars = lazy_variables
def __getitem__(self, key):
if key not in self and key in self.lazy_vars:
self[key] = self.lazy_vars[key]()
return super().__getitem__(key)
def generate_a():
print("generate var a lazily..")
return "<a_large_array>"
# You can add as many variables as you want here
lazy_vars = {'a': generate_a}
lazy = LazyDict(lazy_vars)
# retrieve the variable you need from `lazy`
a = lazy['a']
print("Got a:", a)
And you can actually evaluate a variable lazily if you use exec to run your code. The solution is just using a custom globals.
your_code = "print('inside exec');print(a)"
exec(your_code, lazy)
If you did your_code = open(your_file).read(), you could actually run your code and achieve what you want. But I think the more practical approach would be the former one.

Categories