问题:如何在Python 3中使用自定义比较功能?
在Python 2.x中,我可以将自定义函数传递给sort和.sort函数
>>> x=['kar','htar','har','ar']
>>>
>>> sorted(x)
['ar', 'har', 'htar', 'kar']
>>>
>>> sorted(x,cmp=customsort)
['kar', 'htar', 'har', 'ar']
因为用我的语言,辅音是伴随着这个顺序
"k","kh",....,"ht",..."h",...,"a"
但是在Python 3.x中,看起来我无法传递cmp
关键字
>>> sorted(x,cmp=customsort)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'cmp' is an invalid keyword argument for this function
有其他选择吗?或者我也应该编写自己的排序函数吗?
注意:我通过使用“ k”,“ kh”等进行了简化。实际字符是Unicode,甚至更复杂,有时在辅音前后都有元音,所以我完成了自定义比较功能,因此这一部分还可以。唯一的问题是我无法将自定义比较功能传递给sort或.sort
回答 0
使用key
参数(并按照配方上如何将旧的转换cmp
功能的key
功能)。
functools
cmp_to_key
在docs.python.org/3.6/library/functools.html#functools.cmp_to_key中提到了一个功能
回答 1
使用key
关键字和functools.cmp_to_key转换比较功能:
sorted(x, key=functools.cmp_to_key(customsort))
回答 2
而不是customsort(),您需要一个函数来将每个单词转换为Python已经知道如何排序的东西。例如,您可以将每个单词转换为数字列表,其中每个数字代表每个字母在字母表中的位置。像这样:
my_alphabet = ['a', 'b', 'c']
def custom_key(word):
numbers = []
for letter in word:
numbers.append(my_alphabet.index(letter))
return numbers
x=['cbaba', 'ababa', 'bbaa']
x.sort(key=custom_key)
由于您的语言包括多字符字母,因此您的custom_key函数显然需要更加复杂。那应该给您大致的想法。
回答 3
完整的python3 cmp_to_key lambda示例:
from functools import cmp_to_key
nums = [28, 50, 17, 12, 121]
nums.sort(key=cmp_to_key(lambda x, y: 1 if str(x)+str(y) < str(y)+str(x) else -1))
与普通对象排序相比:
class NumStr:
def __init__(self, v):
self.v = v
def __lt__(self, other):
return self.v + other.v < other.v + self.v
A = [NumStr("12"), NumStr("121")]
A.sort()
print(A[0].v, A[1].v)
A = [obj.v for obj in A]
print(A)
回答 4
我不知道这是否有帮助,但是您可以签出该locale
模块。看起来您可以将语言环境设置为您的语言,并使用locale.strcoll
您的语言的排序规则来比较字符串。
回答 5
请改用key
参数。它采用一个函数,该函数接受要处理的值,并返回单个值,该值给出了用于排序的键。
sorted(x, key=somekeyfunc)