【问题标题】:Convert fractional day of year to Pandas Datetime将一年中的小数天转换为 Pandas 日期时间
【发布时间】:2017-10-20 22:18:34
【问题描述】:

我有一列 Pandas DataFrame 是一年中的小数天 (DOY)。此列显示为:

               DOY
0       200.749967
1       200.791667
2       200.833367
3       200.874967
4       200.916667
5       200.958367
6       200.999967
7       201.041667
       ...    
3491    627.166667
3492    627.333367
3493    627.499967
3494    627.666667
3495    627.833367
3496    627.999967
3497    628.166667
3498    628.333367
Name: DOY, Length: 3499, dtype: float64

起始年份是 2011 年,但 DOY 数据在 2012 年之前继续增加值,而不会在新的一年重置为零。

如何将其转换为格式为“YYYY-MM-DD HH:MM:SS”的 Pandas DatetimeIndex?

【问题讨论】:

    标签: python pandas datetime


    【解决方案1】:

    虽然接受的答案在 DOY 到 Datetime 的转换中是正确的,但是有一个小错误被忽略了。

    任何年份的 1 月 1 日午夜都是 DOY 1.0。当您继续使用小数 DOY 时间时,1 月 1 日 12:00 是 DOY 1.5,1 月 2 日 00:00 是 DOY 2.0,等等...

    如果按照其他答案中的建议将 DOY 时间添加到基本偏移日期,则生成的时间会向前偏移一天。例如,pd.to_datetime('2011-01-01') + pd.to_timedelta(df.DOY, unit='D') 的 DOY 系列以 1.0 开头,导致开始日期为“2011-01-02”,这是不正确的。这是 DOY 时间以 1 而不是 0 开头的约定的结果。有关详细信息,请参阅here。

    因此,正确答案(产生正确的日期时间结果)是:

    df.DOY = pd.to_datetime('2011-1-1') + pd.to_timedelta(gps.DOY, unit='D') - pd.Timedelta(days=1)
    

    【讨论】:

      【解决方案2】:

      只需使用带有适当参数的to_datetime (read the manual):

      >>> pandas.to_datetime([0,0.1,200,400,800], unit='D', origin=pandas.Timestamp('01-01-2011'))
      
      DatetimeIndex(['2011-01-01 00:00:00', '2011-01-01 02:24:00', '2011-07-20 00:00:00', '2012-02-05 00:00:00', '2013-03-11 00:00:00'], dtype='datetime64[ns]', freq=None)
      

      【讨论】:

      • 谢谢,这显然是一个等效且非常好的答案。但是,我接受了来自@COLDSPEED 的答案,其中包括对我的数据的特定应用程序。但当然也赞成这一点。
      • 一定要减去一天才能得到正确的天数。
      【解决方案3】:

      我能想到的一种方法是将您的列转换为TimeDelta,然后将其添加到基本偏移量 (2011/1/1)。

      df.DOY = pd.to_datetime('2011-1-1') + pd.to_timedelta(df.DOY, unit='D')
      print(df.DOY)
      0      2011-07-20 17:59:57.148800
      1      2011-07-20 19:00:00.028800
      2      2011-07-20 20:00:02.908800
      3      2011-07-20 20:59:57.148800
      4      2011-07-20 22:00:00.028800
      5      2011-07-20 23:00:02.908800
      6      2011-07-20 23:59:57.148800 
      7      2011-07-21 01:00:00.028800
             ... 
      3491   2012-09-19 04:00:00.028800
      3492   2012-09-19 08:00:02.908800
      3493   2012-09-19 11:59:57.148800
      3494   2012-09-19 16:00:00.028800
      3495   2012-09-19 20:00:02.908800
      3496   2012-09-19 23:59:57.148800
      3497   2012-09-20 04:00:00.028800
      3498   2012-09-20 08:00:02.908800
      Name: DOY, dtype: datetime64[ns]
      

      另一种方法是使用origin 参数集调用pd.to_datetime,如their answer 中的agtoever 所示。

      【讨论】:

      • 为什么不在to_datetime中使用origin参数?
      • @agtoever 很好,我不知道你可以。 (赞成你的答案)
      • 查看我添加的关于提供正确日期时间结果所需的 1 天偏移量的附加答案。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-02-06
      • 1970-01-01
      • 2019-11-07
      • 1970-01-01
      • 1970-01-01
      • 2014-08-03
      • 1970-01-01
      相关资源
      最近更新 更多