如何在Python3中编写自定义比较器和自定义排序以在sorted()函数中使用。

huangapple go评论102阅读模式
英文:

How to write a custom comparator with custom sort in Python3 to use it in sorted() function

问题

I can provide the translation of the code and the relevant information:

  1. 我目前被困在编写比较器的问题上基本思路是编写一个函数它接受两个参数两个列表),但我想将它用于一个包含这些列表的列表以便在sorted()函数中使用它我该如何做
  2. 比较器
  3. ```python
  4. def dispersion_sort(frec, srec):
  5. if isinstance(frec, intervals.Interval) and isinstance(srec, intervals.Interval):
  6. if frec[DOUBLE_RES_COL] < srec[DOUBLE_RES_COL]:
  7. return frec
  8. if frec[DOUBLE_RES_COL] > srec[DOUBLE_RES_COL]:
  9. return srec
  10. if frec[DOUBLE_RES_COL].overlaps(srec[DOUBLE_RES_COL]):
  11. if (frec[DOUBLE_TIME_COL] < srec[DOUBLE_TIME_COL]):
  12. return frec
  13. else:
  14. return srec
  15. return frec

示例 frec 数据:
['1', 'Mikhail Nitenko', '@login', '✅', [-0.000509228437634554,0.0007110924383354339], datetime.datetime(2020, 1, 2, 14, 46, 46)]

我希望如何调用它:

  1. results = sorted(results, key=dispersion_sort)

非常感谢!

  1. <details>
  2. <summary>英文:</summary>
  3. I&#39;m currently stuck on a problem to write a comparator. The base idea was to write a function, which takes to parameters (two lists), but I want to use it on a list of these lists to use it in sorted() function. How shall I do it?
  4. Comparator:
  5. ```python
  6. def dispersion_sort(frec, srec):
  7. if isinstance(frec, intervals.Interval) and isinstance(srec, intervals.Interval):
  8. if frec[DOUBLE_RES_COL] &lt; srec[DOUBLE_RES_COL]:
  9. return frec
  10. if frec[DOUBLE_RES_COL] &gt; srec[DOUBLE_RES_COL]:
  11. return srec
  12. if frec[DOUBLE_RES_COL].overlaps(srec[DOUBLE_RES_COL]):
  13. if (frec[DOUBLE_TIME_COL] &lt; srec[DOUBLE_TIME_COL]):
  14. return frec
  15. else:
  16. return srec
  17. return frec

Sample frec data:
[&#39;1&#39;, &#39;Mikhail Nitenko&#39;, &#39;@login&#39;, &#39;✅&#39;, [-0.000509228437634554,0.0007110924383354339], datetime.datetime(2020, 1, 2, 14, 46, 46)]

How I wanted to call it:

  1. results = sorted(results, key=dispersion_sort)

Thanks a lot!

答案1

得分: 1

你可以使用 functools.cmp_to_key 来实现这个:

  1. from functools import cmp_to_key
  2. results = sorted(results, key=cmp_to_key(dispersion_sort))

它会将旧式的比较函数(接受两个参数)转换为新式的键函数(接受一个参数)。

英文:

You can use functools.cmp_to_key for this:

  1. from functools import cmp_to_key
  2. results = sorted(results, key=cmp_to_key(dispersion_sort))

It will transform the old style comparator function (which takes two arguments), into a new style key function (which takes one argument).

答案2

得分: 0

Here is the translated code part:

  1. 如果你想显式创建一个比较器你需要实现一个自定义类该类具有以下魔术方法
  2. ```python
  3. class comparator:
  4. def __init__(self, obj, *args):
  5. self.obj = obj
  6. def __lt__(self, other):
  7. return mycmp(self.obj, other.obj) < 0
  8. def __gt__(self, other):
  9. return mycmp(self.obj, other.obj) > 0
  10. def __eq__(self, other):
  11. return mycmp(self.obj, other.obj) == 0
  12. def __le__(self, other):
  13. return mycmp(self.obj, other.obj) <= 0
  14. def __ge__(self, other):
  15. return mycmp(self.obj, other.obj) >= 0
  16. def __ne__(self, other):
  17. return mycmp(self.obj, other.obj) != 0

在这里,函数 mycmp 就像你展示的那样。你也可以选择将你的逻辑直接放入类中。在这里,这些方法应该返回 TrueFalse,这与你当前的函数不同。如果你想直接将当前的函数用于这个类模板,确保相应地进行更改。

一旦你准备好了这个类,你可以直接传递它:key=comparator

  1. <details>
  2. <summary>英文:</summary>
  3. If you wanted to explicitly create a comparator, you&#39;d want to implement a custom class that has that has these magic methods:
  4. ```python
  5. class comparator:
  6. def __init__(self, obj, *args):
  7. self.obj = obj
  8. def __lt__(self, other):
  9. return mycmp(self.obj, other.obj) &lt; 0
  10. def __gt__(self, other):
  11. return mycmp(self.obj, other.obj) &gt; 0
  12. def __eq__(self, other):
  13. return mycmp(self.obj, other.obj) == 0
  14. def __le__(self, other):
  15. return mycmp(self.obj, other.obj) &lt;= 0
  16. def __ge__(self, other):
  17. return mycmp(self.obj, other.obj) &gt;= 0
  18. def __ne__(self, other):
  19. return mycmp(self.obj, other.obj) != 0

Here, the function mycmp is a function like the one you showed. You can also choose to put your logic directly in the class itself. Here, these methods should return a True or False, which is different from your current function. Make sure that is changed accordingly if you want to use the current function directly into this class template.

Once you have the class ready , you can pass it in directly: key=comparator

huangapple
  • 本文由 发表于 2020年1月3日 23:34:57
  • 转载请务必保留本文链接:https://go.coder-hub.com/59581285.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定