You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何优化Python sort_people函数的排序性能?

问题:优化人员排序算法的性能

任务要求实现sort_people(people)函数,接收人员列表并返回排序后的列表,排序规则:

  • 优先按出生日期从年长到年轻排序
  • 出生日期相同时,按姓氏升序排序
  • 姓氏也相同时,按名字升序排序
  • 三项特征均一致时,顺序任意

我原本用functools.cmp_to_key配合自定义比较函数实现,但性能未达标,只拿到5/10分,需要优化排序速度。

我的代码:

import datetime
import functools

def compare_people(p1, p2):
    date1 = datetime.strptime(p1.birth_date, '%d.%m.%Y')
    date2 = datetime.strptime(p2.birth_date, '%d.%m.%Y')

    if date1>date2:
        return 1
    elif date1<date2:
        return -1
    
    if p1.last_name > p2.last_name:
        return 1
    elif p1.last_name < p2.last_name:
        return -1
    
    if p1.first_name > p2.first_name:
        return 1
    elif p1.first_name < p2.first_name:
        return -1
    else:
        return 0

def sort_people(people):
    cmp1 = functools.cmp_to_key(compare_people)
    people.sort(key=cmp1)
    return people

优化方案

你的代码性能瓶颈主要在两点:

  1. cmp_to_key的效率远低于直接使用sort的key参数——比较函数会在每对元素对比时重复调用,时间复杂度为O(n²)级别的函数开销;而key函数仅为每个元素计算一次排序键,开销是O(n)级别。
  2. 每次比较都重复调用datetime.strptime解析日期,同一个日期会被解析多次,浪费大量计算资源。

优化后的基础版本

import datetime

def sort_people(people):
    def get_sort_key(person):
        # 仅解析一次日期,转换为datetime对象
        birth_date = datetime.strptime(person.birth_date, '%d.%m.%Y')
        # 排序键元组:(-日期序数, 姓氏, 名字)
        # 元组按顺序对比元素,完全匹配排序规则
        return (-birth_date.toordinal(), person.last_name, person.first_name)
    
    # 使用key参数排序,性能远高于cmp_to_key
    people.sort(key=get_sort_key)
    return people

优化细节说明

  • 预计算排序键:每个人员的日期仅解析一次,避免重复解析的冗余开销。
  • 元组作为排序键:Python元组会按元素顺序依次比较,完美契合排序规则:
    • -birth_date.toordinal():将日期转换为整数序数后取负,让年长的日期(序数更小)排在前面。
    • 姓氏、名字直接按升序排列,当前面的元素相同时,自动用后续元素继续对比。
  • 弃用cmp_to_key:直接使用sort的key参数是Python排序的最优实践,数据量越大,性能提升越明显。

极致性能版本(跳过datetime解析)

如果数据量极大,还可以跳过datetime模块,直接拆分日期字符串生成排序键,进一步提升速度:

def sort_people(people):
    def get_sort_key(person):
        # 拆分日期字符串,转换为整数元组
        day, month, year = person.birth_date.split('.')
        # 用(-年, -月, -日)实现日期降序,后续拼接姓氏、名字
        return (-int(year), -int(month), -int(day), person.last_name, person.first_name)
    
    people.sort(key=get_sort_key)
    return people

这个版本完全避免了datetime解析的开销,仅通过字符串操作和整数转换生成排序键,性能会比基础版本更优。


内容的提问来源于stack exchange,提问作者some_guy256

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.10 18:50:31