2015-06-09 16 views
6

Momentan erzeuge ich einen DateTimeIndex mit einer bestimmten Funktion, zipline.utils.tradingcalendar.get_trading_days. Die Zeitreihe ist ungefähr täglich, aber mit einigen Lücken.Holen Sie sich das letzte Datum in jedem Monat einer Zeitreihe Pandas

Mein Ziel ist es, das letzte Datum in der DateTimeIndex für jeden Monat zu bekommen.

.to_period('M') & .to_timestamp('M') funktionieren nicht, da sie den letzten Tag des Monats und nicht den letzten Wert der Variablen in jedem Monat angeben.

Als Beispiel, wenn dies meine Zeitreihe ist, möchte ich "2015-05-29" auswählen, während der letzte Tag des Monats "2015-05-31" ist.

['2015-05-18', '2015-05-19', '2015-05-20', '2015-05-21', '2015-05-22', '2015-05 -26 ',' 2015-05-27 ',' 2015-05-28 ', ' 2015-05-29 ',' 2015-06-01 ']

+4

Es wird nicht 'df.groupby ([df.index.year, df. index.month]). last() 'gib was du willst? – EdChum

+0

Nein, das geht leider nicht. Werfen Sie einen Blick auf meinen Beitrag für ein Beispiel. – ikemblem

+0

Ich bin mir nicht sicher, warum Eds Kommentar nicht funktioniert. Ihr Beitrag wird zuerst in einen Punkt konvertiert, während Eds Kommentar nur den letzten Handelstag eines bestimmten Monats für ein bestimmtes Jahr betrachtet. – Alexander

Antwort

2

Die Antwort von Condla kam mir am nächsten, abgesehen davon, dass mein Zeitindex um mehr als ein Jahr gedehnt wurde, musste ich sowohl nach Monat als auch nach Jahr gruppieren und dann das maximale Datum auswählen. Unten ist der Code, mit dem ich gelandet bin.

# tempTradeDays is the initial DatetimeIndex 
dateRange = [] 
tempYear = None 
dictYears = tempTradeDays.groupby(tempTradeDays.year) 
for yr in dictYears.keys(): 
    tempYear = pd.DatetimeIndex(dictYears[yr]).groupby(pd.DatetimeIndex(dictYears[yr]).month) 
    for m in tempYear.keys(): 
     dateRange.append(max(tempYear[m])) 
dateRange = pd.DatetimeIndex(dateRange).order() 
+0

Gefällt mir.Aber vielleicht gibt es heute eine Pandas-Inhouse-Lösung ... – Pat

3

Meine Strategie wäre, nach Monat zu gruppieren und dann wählen Sie die „maximale“ jeder Gruppe:

Wenn „dt“ Ihr DatetimeIndex Objekt ist:

last_dates_of_the_month = [] 
dt_month_group_dict = dt.groupby(dt.month) 
for month in dt_month_group_dict: 
    last_date = max(dt_month_group_dict[month]) 
    last_dates_of_the_month.append(last_date) 

die Liste „last_date_of_the_month“ enthält alle auftretenden letzten Tage, die jeden Monat in Ihrem dat aset. Sie können diese Liste verwenden, um wieder einen DatetimeIndex in Pandas zu erstellen (oder was auch immer Sie damit machen wollen).

1

Vielleicht ist die Antwort nicht mehr benötigt wird, aber während auf die gleiche Frage Suche nach einer Antwort ich vielleicht eine einfachere Lösung gefunden:

import pandas as pd 

sample_dates = pd.date_range(start='2010-01-01', periods=100, freq='B') 
month_end_dates = sample_dates[sample_dates.is_month_end] 
+0

OP sagt klar: "Wenn dies meine Zeitreihe ist, würde ich" 2015-05-29 "wählen, während der letzte Tag des Monats 2015-05- ist. 31 '. " Ihre Lösung würde 2015-05-29 verpassen, da es kein Monatsende ist. –

1

Dies ist eine alte Frage, aber alle vorhandenen hier Antworten sind nicht perfekt. Dies ist die Lösung, die ich kam mit (diesem Datum unter der Annahme einen sortierten Index), die auch in einer Zeile geschrieben werden kann, aber ich spaltete es um Lesbarkeit zu verbessern:

month1 = pd.Series(apple.index.month) 
month2 = pd.Series(apple.index.month).shift(-1) 
mask = (month1 != month2) 
apple[mask.values].head(10) 

paar Noten hier:

  • eine Datetime-Serie Shifting erfordert eine andere Instanz pd.Series
  • Boolean Maske Indizierung .values erfordert (here sehen) (here sehen)

By the way, wenn die Daten, die Werktagen, sind würde es einfacher sein, Resampling zu verwenden: apple.resample('BM')