Python 使用嵌套列表对字典列表进行排序

Python Sorting list of dictionaries with nested list

提问人:badhabit16 提问时间:10/14/2023 更新时间:10/14/2023 访问量:42

问:

我有一个字典列表(消息线程),其中包含另一个字典(消息)列表 我需要按最新消息的日期对线程进行排序。

数据的外观

[
    {key:thread1,
     messages:[
                {key:message1,
                 date:10/10/2023
                 }
                 /// older messages
              ]
    },
    {key:thread2,
     messages: [
                 {key:message4,
                  date:10/13/2023
                  },
                  ///older messages
               ]
      }
]

我需要对它进行排序,以便列表中的第一个是线程 2,该线程 2 的最新消息与线程 1 相关,消息已经正确排序。

列表 字典 排序 数据科学

评论


答:

0赞 Ptolemaic Ptoast 10/14/2023 #1

使用您描述为 的结构数组,可以像这样获得包含最新消息的线程:threads

max(threads,key=lambda x: max(m["date"] for m in x["messages"]))

请注意这些日期参数的格式。如果它们是格式化为月/日/年的字符串,则不会可靠地返回最近的日期。对此的一个解决方法是在执行操作之前将日期参数转换为日期时间对象。max

2赞 DarrylG 10/14/2023 #2

方法

创建一个函数,该函数使用 Python 排序函数,以相反的顺序使用键函数对列表进行排序

法典

from datetime import datetime   # will use strptime in datetime to convert date string to date object

def sort_by_date(lst):
  ' function to sort by the date of the first message in the list '
  # d['messages'][0]['date'] is the date of first message in list
  # use datetime.strptime to convert string to datetime object for sorting
  return sorted(lst, key = lambda d:  datetime.strptime(d['messages'][0]['date'], "%m/%d/%Y"),
               reverse = True)

用法

# List to sort
lst = [
    {'key':'thread1',
     'messages':[
                {'key':'message1',
                 'date':'10/10/2023'
                 }
                 # older messages
              ]
    },
    {'key':'thread2',
     'messages': [
                 {'key':'message4',
                  'date':'10/13/2023'
                  },
                  # older messages
               ]
      }
]

print(sort_by_date(lst))  # Use function sort_by_date defined above

输出

结果是 thread2 是第一个

[{'key': 'thread2', 'messages': [{'key': 'message4', 'date': '10/13/2023'}]}, {'key': 'thread1', 'messages': [{'key': 'message1', 'date': '10/10/2023'}]}]