Skip to main content
 首页 » 编程设计

python之如何创建具有复杂逻辑的自定义排序功能

2025年05月04日17xiaohuochai

我尝试根据一些重要的比较逻辑对对象列表进行排序,但发现这很困难,因为在 Python 中,自定义排序函数只需要一个参数。例如,在 Java 中,排序函数将引用 object1 和 object2,从而可以直接比较它们。

class Point: 
    def __init__(self, char, num, pt_type): 
        self.char = char 
        self.num = num 
        self.pt_type = pt_type  # 'start' or 'end' 
 
    def __str__(self): 
        return str([self.char, str(self.num), self.pt_type]) 
    def __repr__(self): 
        return str(self) 
 
arr = [Point('C', 1, 'end'), Point('C', 9, 'start'), 
       Point('B', 7, 'end'), Point('B', 2, 'end'), 
       Point('A', 3, 'start'), Point('A', 6, 'start')] 
 
def my_sort(key): 
    # Sort by first element (letter).  
    # 
    # If the letter is the same, fallback to sorting by the 
    # 2nd element (number), but the logic of this comparison depends 
    # on `pt_type`: 
    #   -If Point1 and Point2 both have type 'start', pick the higher number first. 
    #   -If Point1 and Point2 both have type 'end', pick the lower number first. 
    #   -If Point1 and Point2 have different types, pick the 'start' type first. 
    return key.char 
 
print(sorted(arr, key=my_sort)) 

预期的排序顺序应该是:

[Point('A', 6, 'start'), Point('A', 3, 'start') 
 Point('B', 2, 'end'), Point('B', 7, 'end'), 
 Point('C', 9, 'start'), Point('C', 1, 'end')] 

我什至不知道如何开始实现所需的逻辑,所以我将不胜感激插入正确的方向。

请您参考如下方法:

我会使用下面的 key 函数:

class Point: 
    def __init__(self, char, num, pt_type): 
        self.char = char 
        self.num = num 
        self.pt_type = pt_type  # 'start' or 'end' 
 
    def __str__(self): 
        return str([self.char, str(self.num), self.pt_type]) 
 
    def __repr__(self): 
        return str(self) 
 
 
arr = [Point('C', 1, 'end'), Point('C', 9, 'start'), 
       Point('B', 7, 'end'), Point('B', 2, 'end'), 
       Point('A', 3, 'start'), Point('A', 6, 'start')] 
 
 
def key(p): 
    return p.char, int(p.pt_type != 'start'), p.num if p.pt_type == 'end' else -1 * p.num 
 
 
result = sorted(arr, key=key) 
print(result) 

输出

[['A', '6', 'start'], ['A', '3', 'start'], ['B', '2', 'end'], ['B', '7', 'end'], ['C', '9', 'start'], ['C', '1', 'end']] 

key 函数创建一个用作键的元组,第一个元素是字母,如果节点类型为“start”,则第二个元素为 0,如果节点类型为“end”,则为 1。如果最后一个元素是“开始”类型,则它是负数;如果它是“结束”类型,则它是正数。