【问题标题】:pandas: how to create a single date column from columns containing year, month, and day? [duplicate]pandas:如何从包含年、月和日的列中创建单个日期列? [复制]
【发布时间】:2019-06-26 11:26:49
【问题描述】:

我有一个看起来像这样的 pandas 数据框:

year month day
2019     1  29
2019     1  30
2019     1  31
2019     2   1

我想创建一个具有正确数据类型的日期列,例如:

year month day date
2019     1  29 2019-01-29
2019     1  30 2019-01-30
2019     1  31 2019-01-31
2019     2   1 2019-02-01

我知道在 Python 中,我可以从它的年/月/日组件中创建一个日期,如下所示:

>>> import datetime
>>> datetime.date(year=2019, month=1, day=29)
datetime.date(2019, 1, 29)

如何将其应用于数据框中的所有行以创建日期列?

【问题讨论】:

    标签: python pandas date


    【解决方案1】:

    这个方法也有效;

    df['combined'] = pd.to_datetime([f'{y}-{m}-{d}' for y, m, d in zip(df.year, df.month, df.day)])
    

    编辑 2019-11-17 回复@HenryHenrinson

    感谢您的 cmets。我确实回去检查性能,看看你是否正确。

    我创建了一个从 1980 年 1 月 1 日到 2019 年 1 月 1 日的数据框。

    df.head()
    
       year  month  day
    0  1980      1    1
    1  1980      1    2
    2  1980      1    3
    3  1980      1    4
    4  1980      1    5
    
    print(df.info())
    
    <class 'pandas.core.frame.DataFrame'>
    RangeIndex: 14246 entries, 0 to 14245
    Data columns (total 3 columns):
    year     14246 non-null int64
    month    14246 non-null int64
    day      14246 non-null int64
    dtypes: int64(3)
    memory usage: 334.0 KB
    None
    

    测试下面的 iterrows 解决方案:

    %timeit [datetime.date(year=x[1].year, month=x[1].month, day=x[1].day) for x in df.iterrows()]
    
    results in: 
    1.23 s ± 30.4 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
    

    测试我的解决方案:

    %timeit pd.Series(pd.to_datetime([f'{y}-{m}-{d}' for y, m, d in zip(df.year, df.month, df.day)]))
    
    results in: 
    9.9 ms ± 159 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
    

    并测试伟大而强大的@wenyoben 的解决方案...

    %timeit pd.to_datetime(df)
    
    results in: 
    8.81 ms ± 206 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
    

    @wenyoben 解决方案最快、最优雅,应该是首选答案。

    【讨论】:

    • 这个解决方案的问题是它返回一列字符串,而不是类似日期时间的对象。
    • @Paul H 你能澄清一下你的说法吗?它在我的代码中显示为 datetime64 。 ------> 组合 4 个非空 datetime64[ns]
    • 哎呀,我看错了。无视我
    • 这很糟糕,因为它需要您构建和解析字符串,效率非常低。
    【解决方案2】:

    这是一种方法

    df1['date'] = [datetime.date(year=x[1].year, month=x[1].month, day=x[1].day) for x in df1.iterrows()]
    

    输出:

       year  month  day        date
    0  2019      1   29  2019-01-29
    1  2019      1   30  2019-01-30
    2  2019      1   31  2019-01-31
    3  2019      2    1  2019-02-01
    

    【讨论】:

    • 哦,已经回答了:(
    • 你不需要像这样迭代 pandas 数据框
    • 魔法在这里尝试pd.to_datetime(df)
    • @Wen-Ben 美丽,再次感谢分享!
    • 您的解决方案更好,因为它不需要构建字符串然后使用 pd.to_datetime 魔法。当您使用 pandas 进行“迭代”时,人们会抱怨,但可以构建十亿个字符串来解析一些日期
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-04-23
    • 2015-10-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-10-15
    • 1970-01-01
    相关资源
    最近更新 更多