【问题标题】:pandas: function equivalent to SQL's datediff()?pandas:相当于 SQL 的 datediff() 的函数?
【发布时间】:2016-05-06 17:37:49
【问题描述】:

在 Python 的 pandas 中是否有等效于 SQL 的 datediff 函数? 这个问题的答案: Add column with number of days between dates in DataFrame pandas 解释了如何计算天数的差异。例如:

>>> (pd.to_datetime('15-10-2010') - pd.to_datetime('15-07-2010')) / pd.offsets.Day(1)
92.0

但是,我有两个问题:

  1. 有没有办法计算月差?我可以将上面的结果近似地除以 30,除以 31,但我想知道是否有一些内置函数可以自动执行此操作。
  2. pd.offsets 的语法是什么?我尝试除以 pd.offsets.Month(1) 并且它不起作用。我在这里查看了文档(这很糟糕,就像所有 Python 的文档一样!):http://pandas.pydata.org/pandas-docs/stable/timeseries.html#dateoffset-objects 但 Day() 不存在,所以我很困惑

【问题讨论】:

  • 另外,我似乎无法将结果转换为整数。有什么想法吗?
  • 嗯,我在这里找到了stackoverflow.com/questions/22132525/… 如何从 timedelta 转换为 float:除以 np.timedelta64(1,'D')。为什么,以及记录在哪里,是单独的问题!!!

标签: python pandas datediff


【解决方案1】:

如果你环顾四周,似乎几个月是不可能摆脱TimeDelta的:

In [193]: date_1 = pd.to_datetime('2015-01-02 12:13:14')

In [194]: date_2 = pd.to_datetime('2012-03-02 12:13:14')

In [195]: date_1 - date_2
Out[195]: Timedelta('1036 days 00:00:00')

In [199]: td_1.
td_1.asm8            td_1.days            td_1.freq            td_1.microseconds    td_1.resolution      td_1.to_pytimedelta  td_1.value           
td_1.ceil            td_1.delta           td_1.is_populated    td_1.min             td_1.round           td_1.to_timedelta64  td_1.view            
td_1.components      td_1.floor           td_1.max             td_1.nanoseconds     td_1.seconds         td_1.total_seconds

In [199]: td_1.components
Out[199]: Components(days=1036, hours=0, minutes=0, seconds=0, milliseconds=0, microseconds=0, nanoseconds=0)

另外,Components 表面上并没有提供相同价值的不同面额,而是

In [213]: td_1.components.days
Out[213]: 1036

In [214]: td_1.components.hours
Out[214]: 0

最终,您到目前为止所做的似乎是“最佳”解决方案:

In [214]: td_1.components.days/30
Out[214]: 34.53333333333333

In [215]: np.round(td_1.components.days/30)
Out[215]: 35.0

In [216]: np.floor(td_1.components.days/30)
Out[216]: 34.0

真的不是什么好消息,但无论如何都是一个解决方案。

关于将 Matlab 附带的文档与 pandas 的文档进行比较,您是对的。但是,如果您要比较两者的价格标签,也许会回答一些问题..(?)

【讨论】:

  • 当然,但我的观点是,在商业环境中,时间就是金钱,而记录不充分的产品的“免费”价格是一种虚假经济。我刚刚浪费了大约一个小时试图弄清楚如何减去日期。如果有一个商业软件,它的功能和 Matlab 的文档质量大致相当,我会立刻买下它
【解决方案2】:

更新:

def months_between(d1, d2):
    dd1 = min(d1, d2)
    dd2 = max(d1, d2)
    return (dd2.year - dd1.year)*12 + dd2.month - dd1.month

In [125]: months_between(pd.to_datetime('2015-01-02 12:13:14'), pd.to_datetime('2012-03-02 12:13:14'))
Out[125]: 34

旧答案:

In [40]: (pd.to_datetime('15-10-2010') - pd.to_datetime('15-07-2010')).days
Out[40]: 92

你也可以这样做几个月:

In [48]: pd.to_datetime('15-10-2010').month - pd.to_datetime('15-07-2010').month
Out[48]: 3

【讨论】:

  • 超级!非常感谢!是我超级笨拙还是熊猫文档真的很糟糕?
  • 实际上,不:这不适用于不同的年份,例如以下仍然返回 3: pd.to_datetime('15-10-2015').month - pd.to_datetime('15- 07-2010').月
  • 这可能是因为您只使用了.month 属性,并没有真正考虑到这两个日期之间有几年的时间。
  • @maxU Matlab 也是如此,但它的文档绝对是一流的。我从来不需要花费数小时来寻找基本问题的答案。时间就是金钱,如果 Matlab 在处理非数值数据方面和 Pandas 一样好,那么许可证的成本就已经收回了
  • @Pythonistaan​​onymous,我已经更新了我的答案 - 请检查
猜你喜欢
  • 2017-05-25
  • 1970-01-01
  • 2018-11-30
  • 1970-01-01
  • 2022-01-02
  • 1970-01-01
  • 2021-12-30
  • 1970-01-01
  • 2018-11-07
相关资源
最近更新 更多