【问题标题】:How to filter your list based on datetime?如何根据日期时间过滤您的列表?
【发布时间】:2021-05-24 17:24:08
【问题描述】:

这是我的清单:

matched_rows_2 =[
    ['1', '07-09-2020', '8:43:02', '100', 'TTF'],
    ['2', '07-09-2020', '8:43:02', '100', 'GGY'],
    ['3', '07-09-2020', '7:53:08', '120', 'HHJ'],
    ['4', '07-09-2020', '7:54:01', '160', 'JJH'],
    ['5', '07-09-2020', '8:30:00', '160', 'RRT'],
    ['6', '07-09-2020', '10:10:10', '160', 'PPO'],
    ['7', '07-09-2020', '11:12:11', '100', 'KKG'],
    ['8', '07-09-2020', '11:31:55', '160', 'PPO']]

我正在尝试执行以下操作:

  1. 对于每个车辆编号 (index[3]),我正在尝试获取日期时间最接近 chosen_datetime 的列表。

我尝试了多种方法,但似乎还没有奏效。 下面是我的鳕鱼e:

chosen_datetime = datetime.fromisoformat("2020-07-09 08:43:55+00:00")
dts = [datetime.strptime(sub[1] + ' ' + sub[2], "%d-%m-%Y  %H:%M:%S").replace(tzinfo=timezone.utc) for sub in matched_rows_2]

for x in matched_rows_2:
    closest_to_chosen_datetime = min(dts, key=lambda d: max( d, chosen_datetime) - min(d, chosen_datetime))
    if closest_to_chosen_datetime:
        print(x)

这是我想要的输出:

['1', '07-09-2020', '8:43:02', '100', 'TTF'],
['2', '07-09-2020', '8:43:02', '100', 'GGY'],
['3', '07-09-2020', '7:53:08', '120', 'HHJ'],
['5', '07-09-2020', '8:30:00', '160', 'RRT'],

这是我当前的输出:

['1', '07-09-2020', '8:43:02', '100', 'TTF'],
['2', '07-09-2020', '8:43:02', '100', 'GGY'],
['3', '07-09-2020', '7:53:08', '120', 'HHJ'],
['4', '07-09-2020', '7:54:01', '160', 'JJH'],
['5', '07-09-2020', '8:30:00', '160', 'RRT'],
['6', '07-09-2020', '10:10:10', '160', 'PPO'],
['7', '07-09-2020', '11:12:11', '100', 'KKG'],
['8', '07-09-2020', '11:31:55', '160', 'PPO']]

我真的不知道发生了什么,出了什么问题。

【问题讨论】:

  • 为什么是两行100?或者车号是index[4]
  • @Epsi95,就是这样。这意味着车辆100 包含 2 个组件
  • 你能用pandas吗?
  • 不,我更喜欢在这个循环中进行。最终我想把它们全部放回一个新列表中
  • 输入不清楚,为什么 100 kkg 不存在?

标签: python list datetime for-loop min


【解决方案1】:

第一个问题是你有一个print 命令你的循环。由于在循环遍历所有项目之前之后您不会知道哪些行的日期时间最接近chosen_datetime,因此这是为时过早的,并且是导致错误输出的重要原因。

其次,因为您正在寻找每辆车最近的日期时间 number 你需要一些逻辑来按车辆分组 号码。

一个选项是使用itertools.groupby 的解决方案;其他 解决方案——我在这里实现的——将结果存储在 以车号为关键字的字典。

以下代码中有几个 cmets,如果有请告诉我 你想要一些额外的细节。

from collections import defaultdict
from datetime import datetime, timezone, timedelta


matched_rows_2 = [
    ['1', '07-09-2020', '8:43:02', '100', 'TTF'],
    ['2', '07-09-2020', '8:43:02', '100', 'GGY'],
    ['3', '07-09-2020', '7:53:08', '120', 'HHJ'],
    ['4', '07-09-2020', '7:54:01', '160', 'JJH'],
    ['5', '07-09-2020', '8:30:00', '160', 'RRT'],
    ['6', '07-09-2020', '10:10:10', '160', 'PPO'],
    ['7', '07-09-2020', '11:12:11', '100', 'KKG'],
    ['8', '07-09-2020', '11:31:55', '160', 'PPO']]

chosen_datetime = datetime.fromisoformat("2020-07-09 08:43:55+00:00")
dts = [
    datetime.strptime(f'{row[1]} {row[2]}', '%m-%d-%Y %H:%M:%S').replace(tzinfo=timezone.utc)
    for row in matched_rows_2
]

mindelta = defaultdict(lambda: None)
minrows = defaultdict(lambda: None)

# use zip() to combine the timestamps in dts with the
# original data
for ts, row in zip(dts, matched_rows_2):
    # get the absolute difference from chosen_datetime
    delta = abs((ts - chosen_datetime).total_seconds())
    vid = row[3]

    # if it's the closest value for this vid (or if we haven't
    # processed the vid yet), update mindelta[vid] with the current
    # delta and set minrows[vid] to the current row.
    if mindelta[vid] is None or delta < mindelta[vid]:
        mindelta[vid] = delta
        minrows[vid] = [row]

    # if the current delta is equal to the existing closest delta,
    # just append the current row.
    elif delta == mindelta[vid]:
        minrows[vid].append(row)

for vid, rows in minrows.items():
    for row in rows:
        print(row)

运行上述程序会产生以下输出:

['1', '07-09-2020', '8:43:02', '100', 'TTF']
['2', '07-09-2020', '8:43:02', '100', 'GGY']
['3', '07-09-2020', '7:53:08', '120', 'HHJ']
['5', '07-09-2020', '8:30:00', '160', 'RRT']

【讨论】:

  • 我们可以就这个代码进行私人协商吗?
  • 我们可以就代码here进行公开对话。
猜你喜欢
  • 1970-01-01
  • 2018-06-17
  • 1970-01-01
  • 2020-05-06
  • 1970-01-01
  • 2014-02-03
  • 2015-03-09
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多