1 回答
TA贡献1876条经验 获得超5个赞
当您有两个(weight, chromo)权重相等的对时会发生错误,此时 Python 会尝试比较这些chromo值:
>>> class Chromo:
... pass
...
>>> chromolist = [Chromo(), Chromo()]
>>> fitness_weights = [42, 42]
>>> sorted(zip(fitness_weights, chromolist))
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: '<' not supported between instances of 'Chromo' and 'Chromo'
您可以通过使用仅提取权重的自定义排序键,或者通过添加对排序序列中的每个值都是唯一的 tie 断路器来避免此问题,例如计数器:
from itertools import count
chromolist = [x for *_, x in sorted(zip(fitness_weights, count(), chromolist))]
计数器只是为了确保 Python 从不查看Chromo实例,因为现在每个元素都是一个(weight, unique_integer, Chromo)元组:
>>> from itertools import count
>>> sorted(zip(fitness_weights, count(), chromolist))
[(42, 0, <__main__.Chromo object at 0x1038cfa00>), (42, 1, <__main__.Chromo object at 0x103a396d0>)]
排序键只是一个生成要比较的值的函数,您可以使用 lambda ( lambda t: t[0]) 或operator.itemgetter()object:
from operator import itemgetter
chromolist = [x for _, x in sorted(zip(fitness_weights, chromolist), key=itemgetter(0))]
key 函数需要单独遍历输入列表,因此速度会稍微慢一些,如这个包含 200 个输入的简单计时赛所示:
>>> from timeit import timeit
>>> fw = fitness_weights * 100
>>> cl = chromolist * 100
>>> timeit('sorted(zip(fw, count(), cl))', globals=globals(), number=100000)
1.4618491119981627
>>> timeit('sorted(zip(fw, cl), key=itemgetter(0))', globals=globals(), number=100000)
1.6409574589997646
添加回答
举报