3

我有一个带有 datetimeindex 索引的数据框。当我尝试按其索引值删除单行时,行数正确变为 N-1,但索引中的时间发生了变化。实际上,从一开始就切掉了一大块行,然后在末尾添加了一大块具有 Nan 值的行。这个“块”的大小似乎是我的时区偏移量*我每小时的频率。这是一个可重现的示例:

Python 2.7.8 |Anaconda 2.1.0 (x86_64)| (default, Aug 21 2014, 15:21:46) 
[GCC 4.2.1 (Apple Inc. build 5577)] on darwin
In[2]: import pandas
In[3]: from pytz import timezone
In[4]: from pandas import Timestamp

In[5]: print pandas.__version__
0.14.0

In[6]: dti = pandas.DatetimeIndex(start='2014-11-09 00:00:00', freq='15T',periods=2976, tz=timezone('US/Pacific'))

In[7]: df = pandas.DataFrame({'data':range(2976)},index=dti)

In[8]: df.head(5)
Out[8]: 
                           data
2014-11-09 00:00:00-08:00     0
2014-11-09 00:15:00-08:00     1
2014-11-09 00:30:00-08:00     2
2014-11-09 00:45:00-08:00     3
2014-11-09 01:00:00-08:00     4

In[9]: df.drop(Timestamp('2014-11-28 11:30:00-08:00')).head(5)
Out[9]: 
                           data
2014-11-09 08:00:00-08:00    32
2014-11-09 08:15:00-08:00    33
2014-11-09 08:30:00-08:00    34
2014-11-09 08:45:00-08:00    35
2014-11-09 09:00:00-08:00    36

In[10]: df.drop(Timestamp('2014-11-28 11:30:00-08:00')).tail(5)
Out[10]: 
                           data
2014-12-10 06:45:00-08:00   NaN
2014-12-10 07:00:00-08:00   NaN
2014-12-10 07:15:00-08:00   NaN
2014-12-10 07:30:00-08:00   NaN
2014-12-10 07:45:00-08:00   NaN

In[11]: df.index
Out[11]: 
<class 'pandas.tseries.index.DatetimeIndex'>
[2014-11-09 00:00:00-08:00, ..., 2014-12-09 23:45:00-08:00]
Length: 2976, Freq: 15T, Timezone: US/Pacific

In[12]: df.drop(Timestamp('2014-11-28 11:30:00-08:00')).index 
Out[12]: 
<class 'pandas.tseries.index.DatetimeIndex'>
[2014-11-09 08:00:00-08:00, ..., 2014-12-10 07:45:00-08:00]
Length: 2975, Freq: None, Timezone: US/Pacific
4

1 回答 1

1

您应该表明您使用的是 0.17.0。

In [13]: import psycopg2

In [14]: df = DataFrame(np.arange(10),index=pd.date_range('20130101 09:00:00',periods=10,tz=psycopg2.tz.FixedOffsetTimezone(offset=-480, name=None),freq='H'),columns=['value'])

In [15]: df
Out[15]: 
                           value
2013-01-01 09:00:00-08:00      0
2013-01-01 10:00:00-08:00      1
2013-01-01 11:00:00-08:00      2
2013-01-01 12:00:00-08:00      3
2013-01-01 13:00:00-08:00      4
2013-01-01 14:00:00-08:00      5
2013-01-01 15:00:00-08:00      6
2013-01-01 16:00:00-08:00      7
2013-01-01 17:00:00-08:00      8
2013-01-01 18:00:00-08:00      9

In [16]: df.index
Out[16]: 
DatetimeIndex(['2013-01-01 09:00:00-08:00', '2013-01-01 10:00:00-08:00', '2013-01-01 11:00:00-08:00', '2013-01-01 12:00:00-08:00', '2013-01-01 13:00:00-08:00', '2013-01-01 14:00:00-08:00',
               '2013-01-01 15:00:00-08:00', '2013-01-01 16:00:00-08:00', '2013-01-01 17:00:00-08:00', '2013-01-01 18:00:00-08:00'],
              dtype='datetime64[ns, psycopg2.tz.FixedOffsetTimezone(offset=-480, name=None)]', freq='H')

In [17]: df.drop(Timestamp('2013-01-01 16:00:00',tz=psycopg2.tz.FixedOffsetTimezone(offset=-480, name=None)))
Out[17]: 
                           value
2013-01-01 09:00:00-08:00      0
2013-01-01 10:00:00-08:00      1
2013-01-01 11:00:00-08:00      2
2013-01-01 12:00:00-08:00      3
2013-01-01 13:00:00-08:00      4
2013-01-01 14:00:00-08:00      5
2013-01-01 15:00:00-08:00      6
2013-01-01 17:00:00-08:00      8
2013-01-01 18:00:00-08:00      9

所以你需要在你要删除的元素上准确地指定时区,否则它不在索引中,否则你会得到一个错误:

In [18]: df.drop(Timestamp('2013-01-01 16:00:00'))
ValueError: labels [Timestamp('2013-01-01 16:00:00')] not contained in axis

所以请提供一个可重现的例子。

此外,您可能希望使用read_sql_table而不是read_sql_query(它确实正确读取了时区列)。

或者,您可能只是想转换为“更有用”的时区(例如 UTC 或类似 US/......)

In [21]: df.index.tz_convert('UTC') 
Out[21]: 
DatetimeIndex(['2013-01-01 17:00:00+00:00', '2013-01-01 18:00:00+00:00', '2013-01-01 19:00:00+00:00', '2013-01-01 20:00:00+00:00', '2013-01-01 21:00:00+00:00', '2013-01-01 22:00:00+00:00',
               '2013-01-01 23:00:00+00:00', '2013-01-02 00:00:00+00:00', '2013-01-02 01:00:00+00:00', '2013-01-02 02:00:00+00:00'],
              dtype='datetime64[ns, UTC]', freq='H')

或者只是放下 tz 并定位它的位置(这就是我认为你想要的)

In [27]: df.index.tz_localize(None)
Out[27]: 
DatetimeIndex(['2013-01-01 09:00:00', '2013-01-01 10:00:00', '2013-01-01 11:00:00', '2013-01-01 12:00:00', '2013-01-01 13:00:00', '2013-01-01 14:00:00', '2013-01-01 15:00:00', '2013-01-01 16:00:00',
               '2013-01-01 17:00:00', '2013-01-01 18:00:00'],
              dtype='datetime64[ns]', freq='H')
于 2015-10-13T21:49:45.920 回答