如何将使用日期时间 df 的 if 语句的 for 循环转换为列表理解

我正在尝试将以下带有 if 语句的 for 循环转换为列表理解。


# Create dictionary to hold results

    trip_counts = {'AM': 0, 'PM': 0}


# Loop over all trips

for trip in onebike_datetimes:

  # Check to see if the trip starts before noon

  if trip['start'].hour < 12:

    # Increment the counter for before noon

    trip_counts["AM"] += 1

  else:

    # Increment the counter for after noon

    trip_counts["PM"] += 1

我试过了


[trip_counts["AM"]+=1 if trip['start'].hour <12 else trip_counts['PM']+= 1 for trip in onebike_datetimes] 

但我不断收到语法错误


弑天下
浏览 177回答 4
4回答

慕娘9325324

您可以使用列表理解(实际上,只是一个生成器表达式),但不是您所想的那样。构建一个AMs 和PMs 的生成器,然后用它来构建一个Counter实例。from collections import Countertrip_counts = Counter(("AM" if trip['start'].hour < 12 else "PM")&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;for trip in onebike_datetimes)一个独立的演示:from collections import Counterfrom types import SimpleNamespaceonebike_datetimes = [&nbsp; &nbsp; {'start': SimpleNamespace(hour=9)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=3)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=14)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=19)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=7)},&nbsp; &nbsp; ]trip_counts = Counter(("AM" if trip['start'].hour < 12 else "PM")&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;for trip in onebike_datetimes)assert trip_counts["AM"] == 3assert trip_counts["PM"] == 2

湖上湖

保留你的 for 循环要清楚得多。如果你真的想使用列表理解,你可以这样做:l = ["AM" if trip["start"].hour < 12 else "PM" for trip in onebike_datetimes]am_count = l.count("AM")trip_counts = {"AM": am_count, "PM": len(l) - am_count}trip_counts(如果你使用这个,你不需要初始化)

芜湖不芜

如果这是DataFrame您正在使用的 pandas,为什么不过滤值并立即对它们求和呢?这样的事情可能会起作用:trip_counts['AM'] = len(trip[trip.loc[:, 'hour'] < 12].index)trip_counts['PM'] = len(trip[trip.loc[:, 'hour'] >= 12].index)编辑:我只是对这里给出的答案进行了一些基准测试,因为有些人认为列表理解会自动更快。正如您所看到的,在这种情况下,常规的 for 循环或多或少具有最佳性能,仅Counter与此处其他答案之一中提到的列表推导的使用相匹配。请注意,我稍微修改了我的 Pandas 实现以匹配我认为您的数据可能的结构(即,不在 DataFrame 中),因此在每次运行时将您的数据转换为 DataFrame 可能会有更多的开销。基准生成此图的代码如下所示:import pandas as pdimport numpy as npfrom collections import Counterfrom types import SimpleNamespaceimport perfplotdef gen_data(n):&nbsp; &nbsp; onebike_datetimes = [&nbsp; &nbsp; {'start': SimpleNamespace(hour=9)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=3)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=14)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=19)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=7)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=14)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=19)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=2)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=20)},&nbsp; &nbsp; {'start': SimpleNamespace(hour=12)},&nbsp; &nbsp; ]*n&nbsp; &nbsp; return onebike_datetimesdef use_vanilla_for(a):#&nbsp; &nbsp; &nbsp;onebike_datetimes = gen_data(n)&nbsp; &nbsp; onebike_datetimes = a&nbsp; &nbsp; trip_counts = {'AM': 0, 'PM': 0}&nbsp; &nbsp; for trip in onebike_datetimes:&nbsp; &nbsp; &nbsp; &nbsp; if trip['start'].hour < 12:&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; trip_counts["AM"] += 1&nbsp; &nbsp; &nbsp; &nbsp; else:&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; trip_counts["PM"] += 1&nbsp; &nbsp; return 1&nbsp; &nbsp;&nbsp;#&nbsp; &nbsp; &nbsp;return trip_countsdef use_list_comp(a):#&nbsp; &nbsp; &nbsp;onebike_datetimes = gen_data(n)&nbsp; &nbsp; onebike_datetimes = a&nbsp; &nbsp; trip_counts = {'AM': 0, 'PM': 0}&nbsp; &nbsp; l = ["AM" if trip["start"].hour < 12 else "PM" for trip in onebike_datetimes]&nbsp; &nbsp; trip_counts = {i: l.count(i) for i in l}&nbsp; &nbsp; return 1#&nbsp; &nbsp; &nbsp;return trip_countsdef use_counter(a):#&nbsp; &nbsp; &nbsp;onebike_datetimes = gen_data(n)&nbsp; &nbsp; onebike_datetimes = a&nbsp; &nbsp; trip_counts = {'AM': 0, 'PM': 0}&nbsp; &nbsp; trip_counts = Counter(("AM" if trip['start'].hour < 12 else "PM")&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;for trip in onebike_datetimes)&nbsp; &nbsp; return 1#&nbsp; &nbsp; &nbsp;return trip_countsdef use_pandas(a):#&nbsp; &nbsp; &nbsp;onebike_datetimes = gen_data(n)&nbsp; &nbsp; onebike_datetimes = a&nbsp; &nbsp; trip = pd.DataFrame(list(map(lambda a: a['start'].hour, onebike_datetimes)), columns=['hrs'])&nbsp; &nbsp; trip_counts = {'AM': 0, 'PM': 0}&nbsp; &nbsp; trip_counts['AM'] = len(trip[trip['hrs'] < 12].index)&nbsp; &nbsp; trip_counts['PM'] = len(trip[trip['hrs'] >= 12].index)&nbsp; &nbsp; return 1#&nbsp; &nbsp; &nbsp;return trip_countsperfplot.show(&nbsp; &nbsp; setup=lambda n: gen_data(n),&nbsp; &nbsp; kernels=[&nbsp; &nbsp; &nbsp; &nbsp; lambda a: use_vanilla_for(a),&nbsp; &nbsp; &nbsp; &nbsp; lambda a: use_list_comp(a),&nbsp; &nbsp; &nbsp; &nbsp; lambda a: use_counter(a),&nbsp; &nbsp; &nbsp; &nbsp; lambda a: use_pandas(a),&nbsp; &nbsp; ],&nbsp; &nbsp; labels=["vanilla_for", "list_comp", "counter", "dataframe"],&nbsp; &nbsp; n_range=[2 ** k for k in range(10)],&nbsp; &nbsp; xlabel="len(a)",)

倚天杖

赋值是语句。语句在列表推导中不可用。使用循环你真的不应该这样做,但为了完整起见:trip_counts = {'AM': 0, 'PM': 0}[trip_counts.__setitem__('AM', trip_counts['AM']+1) if trip['start']['hour'] <12 else trip_counts.__setitem__('PM', trip_counts['PM']+1) for trip in onebike_datetimes]print(f"With list comprehension: {trip_counts}")OUT: With list comprehension: {'AM': 1, 'PM': 2}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Python