2017-10-10 1 views
1

Ich habe 2 Datenrahmen mit Spalte 0 für 'Datum'.Verschmelzen 2 Datenrahmen am nächsten vergangenen Datum

Es gibt mehr sekundäre Daten als Hauptdaten und sie sind unterschiedlich (obwohl zeitlich nahe).

Ich möchte beide Datenrahmen zusammenführen Haupttermine als eine Referenz und die Auswahl sekundärer Daten (Zeilen), die basierend auf dem unmittelbaren Datum vor dem Main-Datum zusammengeführt werden.

main = pd.DataFrame({'Date':pd.to_datetime(
     ['2013-07-23', '2013-10-28', '2014-01-27', '2014-04-23', 
     '2014-07-22', '2014-10-20', '2015-01-27', '2015-04-27', 
     '2015-07-21', '2015-10-27', '2016-01-26', '2016-04-26', '2016-07-26']) }) 

     Date 
0 2013-07-23 
1 2013-10-28 
2 2014-01-27 
3 2014-04-23 
4 2014-07-22 
5 2014-10-20 
6 2015-01-27 
7 2015-04-27 
8 2015-07-21 
9 2015-10-27 
10 2016-01-26 
11 2016-04-26 
12 2016-07-26 

Und

sec = pd.DataFrame({'Date':pd.date_range('2013-07-01',periods=42,freq='1MS')}) 

     Date 
0 2013-07-01 
1 2013-08-01 
2 2013-09-01 
3 2013-10-01 
... 

38 2016-09-01 
39 2016-10-01 
40 2016-11-01 
41 2016-12-01 

Daten sollten mit dieser Logik, obwohl halten nur Datum Main und der Rest der Spalten für beide Datenrahmen zusammengefasst werden:

(sortiert umgekehrter chronologischer Reihenfolge)

MERGED 
     Date Main Date Secondary 
0  2016-07-26 2016-07-01 
1  2016-04-26 2016-04-01 
2  2016-01-26 2016-01-01 
3  2015-10-27 2015-10-01 
4  2015-07-21 2015-07-01 
5  2015-04-27 2015-04-01 
6  2015-01-27 2015-01-01 
7  2014-10-20 2014-10-01 
8  2014-07-22 2014-07-01 
9  2014-04-23 2014-04-01 
10 2014-01-27 2014-01-01 
11 2013-10-28 2013-10-01 
12 2013-07-23 2013-07-01 

Die Lösungen, die ich fand, beziehen sich auf das Zusammenführen von 2 Daten, die am nächsten sind, aber für diesen Fall könnte der nächste Begriff ein sekundäres Datum nach dem Hauptdatum bedeuten, das die "vergangene" Bedingung verletzt.

Merge dataframe on closest date

Dieser sieht ähnlich aus, obwohl ich nicht weiß, wie man es auf meinen Fall anwendet.

How to merge two dataframes based on the closest (or most recent) timestamp

+0

'pd.merge_asof()' – DJK

+0

Thanks @ djk47463! Ich sehe, dass es einen Parameter Toleranz = pd.Timedelta() gibt, aber wenn ich es richtig verstehe, findet es den nächsten Wert (könnte Zukunft sein). Wie geht es in die Vergangenheit? – Diego

+0

Es funktioniert nur in der Vergangenheit am engsten, schauen Sie sich den 'allow_exact_matches' Parameter – DJK

Antwort

1

Hier ist ein Versuch mit merge_asof:

df = pd.merge_asof(main.set_index('Date').sort_index(), 
        sec.set_index('Date',drop=False).sort_index(), 
        left_index=True, 
        right_index=True, 
        direction='backward') # backward is the default, so you 
              # can leave this out if you prefer 

df.rename(columns={'Date':'Date_sec'})\ 
    .sort_index(ascending=False).reset_index() 

A Syntax Hinweis: Die drop=False notwendig ist, um sicherzustellen, dass das Datum von dem sekundären Datenrahmen erhalten bleibt. Ohne es enthält das zusammengeführte Datenframe nur das Datum aus dem Hauptdatenframe.

Ergebnisse:

  Date Date_sec 
0 2016-07-26 2016-07-01 
1 2016-04-26 2016-04-01 
2 2016-01-26 2016-01-01 
3 2015-10-27 2015-10-01 
4 2015-07-21 2015-07-01 
5 2015-04-27 2015-04-01 
6 2015-01-27 2015-01-01 
7 2014-10-20 2014-10-01 
8 2014-07-22 2014-07-01 
9 2014-04-23 2014-04-01 
10 2014-01-27 2014-01-01 
11 2013-10-28 2013-10-01 
12 2013-07-23 2013-07-01 
+0

Vielen Dank, aus irgendeinem Grund bekomme ich TypeError: merge_asof() hat ein unerwartetes Keyword-Argument 'Richtung' – Diego

+0

@Die Sie haben wahrscheinlich eine ältere Version von Pandas. Ich glaube, dass "direction" in 0.20.0 hinzugefügt wurde, aber "backward" ist der Standard, also kannst du es wahrscheinlich einfach weglassen. Ich habe es hier nur zur besseren Übersicht hinzugefügt, da es manchmal besser ist, explizit mit Schlüsselwortargumenten zu arbeiten, auch wenn dies unnötig ist. – JohnE

+1

Sie haben Recht! Pandas aufgerüstet. Jetzt bekomme ich TypeError: 'NoneType' -Objekt ist nicht auf Right_Index = True aufrufbar. Recherchiert, konnte aber keine Hinweise finden ... – Diego

Verwandte Themen