[python] Pandas timeseries 플롯 설정 x 축 주 및 부 눈금 및 레이블

Pandas 시계열 객체에서 플로팅 된 시계열 그래프에 대한 주요 및 보조 xtick 및 레이블을 설정할 수 있기를 원합니다.

Pandas 0.9 “새로운 기능”페이지 내용 :

“to_pydatetime을 사용하거나 타임 스탬프 유형에 대한 변환기를 등록 할 수 있습니다.”

그러나 matplotlib ax.xaxis.set_major_locatorax.xaxis.set_major_formatter(및 사소한) 명령을 사용할 수 있도록 그렇게하는 방법을 알아낼 수 없습니다 .

팬더 시간을 변환하지 않고 사용하면 x 축 눈금과 레이블이 잘못됩니다.

‘xticks’매개 변수를 사용하여 주요 눈금을 pandas.plot에 전달한 다음 주요 눈금 레이블을 설정할 수 있습니다. 이 접근법을 사용하여 사소한 틱을 수행하는 방법을 알아낼 수 없습니다. (pandas.plot에서 설정 한 기본 보조 눈금에 레이블을 설정할 수 있습니다)

내 테스트 코드는 다음과 같습니다.

import pandas
print 'pandas.__version__ is ', pandas.__version__
print 'matplotlib.__version__ is ', matplotlib.__version__

dStart = datetime.datetime(2011,5,1) # 1 May
dEnd = datetime.datetime(2011,7,1) # 1 July    

dateIndex = pandas.date_range(start=dStart, end=dEnd, freq='D')
print "1 May to 1 July 2011", dateIndex

testSeries = pandas.Series(data=np.random.randn(len(dateIndex)),
                           index=dateIndex)

ax = plt.figure(figsize=(7,4), dpi=300).add_subplot(111)
testSeries.plot(ax=ax, style='v-', label='first line')

# using MatPlotLib date time locators and formatters doesn't work with new
# pandas datetime index
ax.xaxis.set_minor_locator(matplotlib.dates.WeekdayLocator(byweekday=(1),
                                                           interval=1))
ax.xaxis.set_minor_formatter(matplotlib.dates.DateFormatter('%d\n%a'))
ax.xaxis.grid(True, which="minor")
ax.xaxis.grid(False, which="major")
ax.xaxis.set_major_formatter(matplotlib.dates.DateFormatter('\n\n\n%b%Y'))
plt.show()

# set the major xticks and labels through pandas
ax2 = plt.figure(figsize=(7,4), dpi=300).add_subplot(111)
xticks = pandas.date_range(start=dStart, end=dEnd, freq='W-Tue')
print "xticks: ", xticks
testSeries.plot(ax=ax2, style='-v', label='second line',
                xticks=xticks.to_pydatetime())
ax2.set_xticklabels([x.strftime('%a\n%d\n%h\n%Y') for x in xticks]);
# set the text of the first few minor ticks created by pandas.plot
#    ax2.set_xticklabels(['a','b','c','d','e'], minor=True)
# remove the minor xtick labels set by pandas.plot 
ax2.set_xticklabels([], minor=True)
# turn the minor ticks created by pandas.plot off 
# plt.minorticks_off()
plt.show()
print testSeries['6/4/2011':'6/7/2011']

및 출력 :

pandas.__version__ is  0.9.1.dev-3de54ae
matplotlib.__version__ is  1.1.1
1 May to 1 July 2011 <class 'pandas.tseries.index.DatetimeIndex'>
[2011-05-01 00:00:00, ..., 2011-07-01 00:00:00]
Length: 62, Freq: D, Timezone: None

xaxis에 이상한 날짜가있는 그래프

xticks:  <class 'pandas.tseries.index.DatetimeIndex'>
[2011-05-03 00:00:00, ..., 2011-06-28 00:00:00]
Length: 9, Freq: W-TUE, Timezone: None

정확한 날짜로 그래프

2011-06-04   -0.199393
2011-06-05   -0.043118
2011-06-06    0.477771
2011-06-07   -0.033207
Freq: D

업데이트 : 루프를 사용하여 주요 xtick 레이블을 빌드함으로써 원하는 레이아웃에 더 가까워 질 수있었습니다.

# only show month for first label in month
month = dStart.month - 1
xticklabels = []
for x in xticks:
    if  month != x.month :
        xticklabels.append(x.strftime('%d\n%a\n%h'))
        month = x.month
    else:
        xticklabels.append(x.strftime('%d\n%a'))

그러나 이것은 ax.annotate가능하지만 이상적이지 않은 사용하여 x 축을 수행하는 것과 약간 비슷합니다 .



답변

둘 다 pandas및 진드기를 찾는 데 matplotlib.dates사용 matplotlib.units됩니다.

그러나 matplotlib.dates수동으로 눈금을 설정하는 편리한 방법이 있지만 pandas는 지금까지 자동 서식 지정에 중점을 두는 것으로 보입니다 ( pandas에서 날짜 변환 및 서식 지정에 대한 코드 를 볼 수 있음 ).

따라서 현재로서는 사용하는 것이 더 합리적으로 보입니다 matplotlib.dates(@BrenBarn이 그의 의견에서 언급했듯이).

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import matplotlib.dates as dates

idx = pd.date_range('2011-05-01', '2011-07-01')
s = pd.Series(np.random.randn(len(idx)), index=idx)

fig, ax = plt.subplots()
ax.plot_date(idx.to_pydatetime(), s, 'v-')
ax.xaxis.set_minor_locator(dates.WeekdayLocator(byweekday=(1),
                                                interval=1))
ax.xaxis.set_minor_formatter(dates.DateFormatter('%d\n%a'))
ax.xaxis.grid(True, which="minor")
ax.yaxis.grid()
ax.xaxis.set_major_locator(dates.MonthLocator())
ax.xaxis.set_major_formatter(dates.DateFormatter('\n\n\n%b\n%Y'))
plt.tight_layout()
plt.show()

pandas_like_date_fomatting

(제 로케일은 독일어이므로 화요일 [화]는 Dienstag [Di]가 됨)


답변