Đây là một cách: Về cơ bản, bạn viết lại hàm sắp xếp của mình để lấy danh sách các hàm sắp xếp, mỗi hàm sắp xếp so sánh các thuộc tính bạn muốn kiểm tra, trên mỗi bài kiểm tra sắp xếp, bạn xem và xem hàm cmp có trả về giá trị khác không nếu vậy phá vỡ và gửi giá trị trả lại. Bạn gọi nó bằng cách gọi Lambda của một chức năng của một danh sách Lambdas.
Ưu điểm của nó là nó không truyền dữ liệu đơn lẻ mà không phải là một loại sắp xếp trước đó như các phương pháp khác làm. Một điều nữa là nó sắp xếp tại chỗ, trong khi sắp xếp dường như tạo một bản sao.
Tôi đã sử dụng nó để viết một hàm xếp hạng, xếp hạng danh sách các lớp trong đó mỗi đối tượng nằm trong một nhóm và có chức năng cho điểm, nhưng bạn có thể thêm bất kỳ danh sách các thuộc tính nào. Lưu ý rằng không giống như lambda, mặc dù hackish sử dụng lambda để gọi một setter. Phần xếp hạng sẽ không hoạt động cho một loạt các danh sách, nhưng sắp xếp sẽ.
#First, here's a pure list version
my_sortLambdaLst = [lambda x,y:cmp(x[0], y[0]), lambda x,y:cmp(x[1], y[1])]
def multi_attribute_sort(x,y):
r = 0
for l in my_sortLambdaLst:
r = l(x,y)
if r!=0: return r #keep looping till you see a difference
return r
Lst = [(4, 2.0), (4, 0.01), (4, 0.9), (4, 0.999),(4, 0.2), (1, 2.0), (1, 0.01), (1, 0.9), (1, 0.999), (1, 0.2) ]
Lst.sort(lambda x,y:multi_attribute_sort(x,y)) #The Lambda of the Lambda
for rec in Lst: print str(rec)
Đây là một cách để xếp hạng danh sách các đối tượng
class probe:
def __init__(self, group, score):
self.group = group
self.score = score
self.rank =-1
def set_rank(self, r):
self.rank = r
def __str__(self):
return '\t'.join([str(self.group), str(self.score), str(self.rank)])
def RankLst(inLst, group_lambda= lambda x:x.group, sortLambdaLst = [lambda x,y:cmp(x.group, y.group), lambda x,y:cmp(x.score, y.score)], SetRank_Lambda = lambda x, rank:x.set_rank(rank)):
#Inner function is the only way (I could think of) to pass the sortLambdaLst into a sort function
def multi_attribute_sort(x,y):
r = 0
for l in sortLambdaLst:
r = l(x,y)
if r!=0: return r #keep looping till you see a difference
return r
inLst.sort(lambda x,y:multi_attribute_sort(x,y))
#Now Rank your probes
rank = 0
last_group = group_lambda(inLst[0])
for i in range(len(inLst)):
rec = inLst[i]
group = group_lambda(rec)
if last_group == group:
rank+=1
else:
rank=1
last_group = group
SetRank_Lambda(inLst[i], rank) #This is pure evil!! The lambda purists are gnashing their teeth
Lst = [probe(4, 2.0), probe(4, 0.01), probe(4, 0.9), probe(4, 0.999), probe(4, 0.2), probe(1, 2.0), probe(1, 0.01), probe(1, 0.9), probe(1, 0.999), probe(1, 0.2) ]
RankLst(Lst, group_lambda= lambda x:x.group, sortLambdaLst = [lambda x,y:cmp(x.group, y.group), lambda x,y:cmp(x.score, y.score)], SetRank_Lambda = lambda x, rank:x.set_rank(rank))
print '\t'.join(['group', 'score', 'rank'])
for r in Lst: print r