【问题标题】:Fastest way to check for, and prevent adding duplicate to list of dictionaries检查并防止将重复项添加到字典列表的最快方法
【发布时间】:2022-01-11 06:28:12
【问题描述】:

检查现有列表并防止向此类列表添加重复项的最快方法是:

{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 13, 586785), 'value': Decimal('42362.34'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 17, 827149), 'value': Decimal('42362.35'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 24, 291007), 'value': Decimal('42362.35'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 33, 767991), 'value': Decimal('42362.45'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 35, 880753), 'value': Decimal('42362.60'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 40, 135887), 'value': Decimal('42362.60'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 44, 481802), 'value': Decimal('42362.75'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 46, 618369), 'value': Decimal('42362.95'), 'metric': 'LastPrice'}
{'contract_id': 514750, 'value_at': datetime.datetime(2021, 12, 4, 21, 59, 50, 894044), 'value': Decimal('42362.98'), 'metric': 'LastPrice'}

我考虑只检查列表中现有词典的最后 25 个项目,因为它将每秒更新一次(或更快)。由于数据库写入滞后,我可能不会选择迭代中注册的所有内容,因此我需要“回滚”几秒钟(这可能会导致重复)。运行,每次迭代,通过整个列表(可能包含自午夜以来注册的每三分之一秒)可能是性能杀手。还是有更复杂的方法?

我已经读到,添加到数据帧的操作很慢(而且我认为每次调用 drop_duplicates 方法也不是解决方案),因此提供一个列表对于数据帧(构造函数)来说是最好的。因此,我认为列表会更好。以下是提到的一些基准/示例: Remove duplicate dict in list in Python python remove duplicate dictionaries from a list 但这些通常将列表作为一个整体(而不是其中的一部分)。

【问题讨论】:

  • if ... in set(data) 可能是一个不错的起点 - 数据会删除所有重复项。或者你可以检查if list(set(data)) == data -> duplicates if false, none if true
  • 你可以使用 dicts 的 dict 代替 dicts 的列表吗?由于它是一个字典列表,因此 set() 将无法对字典进行哈希处理,但我认为 set 操作是一种好方法。 dicts 将允许 O(1) 查找时间,使用示例中的任何值将行限定为重复项,作为 dicts 的键。在添加新行之前,您将检查键中是否已存在值,然后从那里继续。
  • 谢谢@Eric,我可以将其更改为字典的字典(使用日期时间作为键)。使用 itertools.islice 库,我可以获得全局 dict 的最后 n 个项目(我假设它就像 C 中的过去一样快,当跳转到顺序内存中的数组元素时,它只是 n * 元素大小(指针大小或结构)虽然我可能已经读过 Python 可能会以不同的方式组织它 - 特别是当元素大小不恒定时)并出于速度原因使用它在较小的子集中进行字典重复键查找。

标签: python list performance dictionary duplicates


【解决方案1】:

解决方案将取决于您认为列表中的“唯一键”。如果它只是“value_at”的时间戳并且数据库按时间戳顺序添加行,那么您可以跟踪您在上一个查询中获得的高水位标记(最高“value_at”)并将其用作标准下一个查询。

另一种策略可能是在获取数据之前从列表中删除满足下一个查询条件的值(假设您将取回它们)。

一个简单粗暴的解决方案是根据您打算使用的下一个标准创建一组您从查询中获得的重叠数据,并根据该组过滤掉新数据。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-04-16
    • 1970-01-01
    • 2010-11-21
    • 2017-05-11
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多