问题
users = [{'name': 'u2', 'age': 18, 'foo': 'a'},
{'name': 'coldplay', 'age': 19, 'foo': 'b'},
{'name': 'pink floyd', 'age': 25, 'foo': 'c'},
{'name': 'the door', 'age': 15, 'foo': 'd'},
{'name': 'eminem', 'age':40, 'foo': 'e'},
{'name': '2pac', 'age':50, 'foo': 'f'},
{'name': 'armstrong', 'age':60, 'foo': 'g'},
{'name': 'ABBA', 'age':25, 'foo': 'h'}
]
按年龄排序
operator.itemgetter
from operator import itemgetter
print sorted(users, key=itemgetter('age'))
上面的结果中,我们发现有两个元素age相同,我们希望如果年龄相同,则按姓名排序呢?事实上,itemgetter可以传入两个参数。
print sorted(users, key=itemgetter('age','name'))
如果要给不支持比较操作的对象排序呢?
class Foo:
def __init__(self,x):
self.x = x
test = [Foo(12), Foo(23),Foo(5),Foo(3),Foo(8),Foo(66)]
test = sorted(test)
for t in test:
print t.x
上面的代码中,我们创建了一个新的类,试图给一组Foo类的对象进行排序,但是失败了。思考一下,为啥int之间可以比较呢?原因很简单,因为int实现了cmp方法
print int.__cmp__
要想让Foo对象可以排序,首先我们要给Foo对象实现cmp方法
class Foo:
def __init__(self,x):
self.x = x
def __cmp__(self, other):
if self.x < other.x:
return -1
elif self.x > other.x:
return 1
else:
return 0
assert Foo(13) > Foo(12)
assert Foo(12) == Foo(12)
assert Foo(11) < Foo(12)
test = [Foo(12), Foo(23),Foo(5),Foo(3),Foo(8),Foo(66)]
test = sorted(test)
for t in test:
print t.x
现在Foo类的对象可比较了,也就可以排序了。
operator.attrgetter
from operator import attrgetter
test = [Foo(12), Foo(23),Foo(5),Foo(3),Foo(8),Foo(66)]
test2 = sorted(test, key=lambda t : t.x)
test1 = sorted(test, key=attrgetter('x'))