Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Making an object's attributes iterable

I'm getting returned a list with objects that have multiple attributes like so:

results = q.fetch(5)
for p in results:
    print "%s %s, %d inches tall" % (p.first_name, p.last_name, p.height

Is it possible to iterate over these attributes so I can do something like for x in p. I want to check the value of each one, but I don't want to create a huge block of IF statements.

like image 933
joslinm Avatar asked Jul 12 '26 07:07

joslinm


2 Answers

I warn against doing this. There are rare exceptions where it's warranted, but almost all the time it's better avoiding this sort of hackish solution. If you want to though, you could use vars() to get a dictionary of attributes and iterate through it. As @Nick points out below, App Engine uses properties instead of values to define its members so you have to use getattr() to get their values.

results = q.fetch(5)
for p in results:
    for attribute in vars(p).keys()
        print '%s = %s' % (attribute, str(getattr(p, attribute)))

Demonstration of what vars() does:

>>> class A:
...     def __init__(self, a, b):
...         self.a = a
...         self.b = b
... 
>>> a = A(1, 2)
>>> vars(a)
{'a': 1, 'b': 2}
>>> for attribute in vars(a).keys():
...     print '%s = %s' % (attribute, str(getattr(a, attribute)))
... 
a = 1
b = 2
like image 132
moinudin Avatar answered Jul 13 '26 21:07

moinudin


You can subclass the original variable type, and define your own cunning iter(self) function, to get what you want. e.g. to change the way a dictionary iterates:-

>>> class mydict(dict):
...    def __iter__(self):
...      for i in self.items():
...          yield i
... 
>>> x = mydict( {'a' : 1, 'b':2 } )
>>> for i in x:
...   print i
... 
('a', 1)
('b', 2)
like image 22
Alex Leach Avatar answered Jul 13 '26 19:07

Alex Leach