Differenza (e) tra merge () e concat () nei panda


89

Qual è la differenza essenziale tra pd.DataFrame.merge()e pd.concat()?

Finora, questo è ciò che ho trovato, per favore commenta quanto è completa e accurata la mia comprensione:

  • .merge()può usare solo colonne (più indici di riga) ed è semanticamente adatto per operazioni in stile database. .concat()può essere utilizzato con entrambi gli assi, utilizzando solo indici e offre la possibilità di aggiungere un indice gerarchico.

  • Per inciso, ciò consente la seguente ridondanza: entrambi possono combinare due frame di dati utilizzando gli indici delle righe.

  • pd.DataFrame.join() offre semplicemente una scorciatoia per un sottoinsieme dei casi d'uso di .merge()

(Pandas è ottimo nell'affrontare un ampio spettro di casi d'uso nell'analisi dei dati. Può essere un po 'scoraggiante esplorare la documentazione per capire qual è il modo migliore per eseguire una determinata attività.)


3
Inoltre, correlato: stackoverflow.com/a/37891437/1972495 una discussione intorno a .merge()e .join().
WindChimes

2
Su merge, join e concat, trovo che questa risposta sia molto chiara su come possono essere utilizzati tutti per fare le stesse cose (sembrano essere solo un'interfaccia alternativa alla stessa funzionalità). Grazie alla tua domanda (e alla risposta che linki nel commento) so finalmente di capire come sono correlati l'unione e l'unione. Non mi è ancora chiaro se concat utilizzi un'implementazione diversa o meno (immagino che dovrò guardare il codice sorgente ...)
pietroppeter

Risposte:


79

Una differenza di livello molto alto è che merge()viene utilizzata per combinare due (o più) dataframe sulla base di valori di colonne comuni (gli indici possono anche essere utilizzati, utilizzare left_index=Truee / o right_index=True), e concat()viene utilizzata per aggiungere uno (o più) dataframe uno sotto l'altro (o lateralmente, a seconda che l' axisopzione sia impostata su 0 o 1).

join()viene utilizzato per unire 2 frame di dati sulla base dell'indice; invece di usare merge()con l'opzione left_index=Trueche possiamo usare join().

Per esempio:

df1 = pd.DataFrame({'Key': ['b', 'b', 'a', 'c', 'a', 'a', 'b'], 'data1': range(7)})

df1:
   Key  data1
0   b   0
1   b   1
2   a   2
3   c   3
4   a   4
5   a   5
6   b   6

df2 = pd.DataFrame({'Key': ['a', 'b', 'd'], 'data2': range(3)})

df2:
    Key data2
0   a   0
1   b   1
2   d   2

#Merge
# The 2 dataframes are merged on the basis of values in column "Key" as it is 
# a common column in 2 dataframes

pd.merge(df1, df2)

   Key data1 data2
0   b    0    1
1   b    1    1
2   b    6    1
3   a    2    0
4   a    4    0
5   a    5    0

#Concat
# df2 dataframe is appended at the bottom of df1 

pd.concat([df1, df2])

   Key data1 data2
0   b   0     NaN
1   b   1     NaN
2   a   2     NaN
3   c   3     NaN
4   a   4     NaN
5   a   5     NaN
6   b   6     NaN
0   a   Nan   0
1   b   Nan   1
2   d   Nan   2

Quindi, questo significa che l'argomento howin mergeopere e media totalmente diverso da quello che fa in concat?
Hemanth Bakaya,

11

pd.concatprende Iterablecome argomento. Quindi, non può prendere DataFramedirettamente s come argomento. Anche le Dimensions del DataFramedovrebbero corrispondere lungo l'asse durante la concatenazione.

pd.mergepuò prendere DataFrames come argomento e viene utilizzato per combinare due DataFrames con le stesse colonne o indice, cosa che non può essere eseguita pd.concatpoiché mostrerà la colonna ripetuta nel DataFrame.

Mentre join può essere utilizzato per unire due DataFrames con indici diversi.


7
Mi piace questa risposta perché afferma che le dimensioni dovrebbero corrispondere durante la concatenazione. concatnon è altro che incollare diversi frame di dati uno sopra l'altro. Non è consapevole del contenuto, nel senso che mostrerà solo due volte la stessa colonna. Considerando mergeche effettivamente uniranno le colonne quando sono uguali.
jorijnsmit

3
Penso che non sia vero. Anche la risposta sopra (di @Abhishek Sawant) fornisce un esempio di concatdove le dimensioni non corrispondono.
michcio1234

7

Attualmente sto cercando di capire le differenze essenziali tra pd.DataFrame.merge()e pd.concat().

Bella domanda. La differenza principale:

pd.concat funziona su entrambi gli assi.

L'altra differenza è che pd.concatha solo join predefiniti interni ed esterni , mentre ha join predefiniti sinistro , destro , esterno e interno .pd.DataFrame.merge()

Terza altra differenza degna di nota è: pd.DataFrame.merge()ha la possibilità di impostare i suffissi di colonna quando si uniscono colonne con lo stesso nome, mentre per pd.concatquesto non è possibile.


Con pd.concatper impostazione predefinita puoi impilare righe di più dataframe ( axis=0) e quando imposti il axis=1, imiti la pd.DataFrame.merge()funzione.

Alcuni esempi utili di pd.concat:

df2=pd.concat([df]*2, ignore_index=True) #double the rows of a dataframe

df2=pd.concat([df, df.iloc[[0]]]) # add first row to the end

df3=pd.concat([df1,df2], join='inner', ignore_index=True) # concat two df's

6

Ad alto livello:

  • .concat()impila semplicemente più DataFrameinsieme verticalmente o punti orizzontalmente dopo l'allineamento sull'indice
  • .merge()prima allinea due DataFramecolonne o indici comuni selezionati, quindi preleva le colonne rimanenti dalle righe allineate di ciascuna DataFrame.

Nello specifico .concat():

  • È una funzione panda di primo livello
  • Combina due o più panda DataFrame verticalmente o orizzontalmente
  • Si allinea solo sull'indice quando si combina orizzontalmente
  • Errori quando uno qualsiasi di DataFramecontiene un indice duplicato.
  • Il valore predefinito è outer join con l'opzione per inner join

E .merge():

  • Esiste sia come funzione panda di primo livello che come DataFramemetodo (a partire da panda 1.0)
  • Combina esattamente due in DataFrameorizzontale
  • Allinea la chiamata DataFrame's colonna (s) o di un indice con l'altro DataFrame' s colonna (s) o di un indice
  • Gestisce i valori duplicati sulle colonne o sull'indice di unione eseguendo un prodotto cartesiano
  • Il valore predefinito è inner join con opzioni per sinistra, esterna e destra

Si noti che durante l'esecuzione pd.merge(left, right), se leftha due righe contenenti gli stessi valori dalle colonne o dall'indice di unione, ogni riga si combinerà con rightle righe corrispondenti di s risultando in un prodotto cartesiano. D'altra parte, se .concat()viene utilizzato per combinare colonne, dobbiamo assicurarci che non esista alcun indice duplicato in nessuno dei due DataFrame.

In pratica:

  • Considera .concat()prima quando combini omogeneo DataFrame, mentre considera .merge()prima quando combini complementare DataFrame.
  • Se è necessario unire verticalmente, andare con .concat(). Se è necessario unire orizzontalmente tramite colonne, andare con .merge(), che per impostazione predefinita si fondono sulle colonne in comune.

Riferimento: Pandas 1.x Cookbook


2

La principale differenza tra merge e concat è che l'unione ti consente di eseguire un "join" più strutturato di tabelle in cui l'uso di concat è più ampio e meno strutturato.

Unisci

Fare riferimento alla documentazione , pd.DataFrame.mergeprende come argomento richiesto il diritto , che puoi pensare come unire la tabella sinistra e la tabella destra secondo alcune operazioni di join strutturato predefinite. Notare la definizione del parametro right .

Parametri obbligatori

  • a destra : DataFrame o Series denominato

Parametri opzionali

  • come : {'left', 'right', 'outer', 'inner'} default 'inner'
  • su : etichetta o elenco
  • left_on : etichetta o elenco o simile a un array
  • right_on : etichetta o elenco o simile a un array
  • left_index : bool, valore predefinito False
  • right_index : bool, valore predefinito False
  • ordinare : bool, valore predefinito False
  • suffissi : tupla di (str, str), predefinito ('_x', '_y')
  • copia : bool, valore predefinito True
  • indicatore : bool o str, valore predefinito False
  • validate : str, opzionale

Importante: pd.DataFrame.merge richiede il diritto di essere un pd.DataFrameo nominatopd.Series oggetto con .

Produzione

  • ritorna : DataFrame

Inoltre, se controlliamo la docstring per l'operazione di unione sui panda è di seguito:

Eseguire un'operazione di unione del database (SQL) tra due oggetti DataFrame o Series utilizzando le colonne come chiavi o i relativi indici di riga

Concat

Fare riferimento alla documentazione di pd.concat, innanzitutto notare che il parametro non è denominato come tabella, data_frame, serie, matrice , ecc., Ma invece objs . Cioè, puoi passare molti "contenitori di dati", che sono definiti come:

Iterable[FrameOrSeriesUnion], Mapping[Optional[Hashable], FrameOrSeriesUnion]

Parametri obbligatori

  • objs : una sequenza o mappatura di oggetti Series o DataFrame

Parametri opzionali

  • asse : {0 / "indice", 1 / "colonne"}, valore predefinito 0
  • join : {'inner', 'outer'}, default 'outer'
  • ignore_index : bool, valore predefinito False
  • tasti : sequenza, default Nessuno
  • livelli : elenco di sequenze, predefinito Nessuno
  • nomi : elenco, predefinito Nessuno
  • verifica_integrità : bool, valore predefinito False
  • ordinare : bool, valore predefinito False
  • copia : bool, valore predefinito True

Produzione

  • Restituisce : oggetto, tipo di obj

Esempio

Codice

import pandas as pd

v1 = pd.Series([1, 5, 9, 13])
v2 = pd.Series([10, 100, 1000, 10000])
v3 = pd.Series([0, 1, 2, 3])

df_left = pd.DataFrame({
    "v1": v1,
    "v2": v2,
    "v3": v3
    })
df_right = pd.DataFrame({
    "v4": [5, 5, 5, 5],
    "v5": [3, 2, 1, 0]
    })


df_concat = pd.concat([v1, v2, v3])

# Performing operations on default

merge_result = df_left.merge(df_right, left_index=True, right_index=True)
concat_result = pd.concat([df_left, df_right], sort=False)
print(merge_result)
print('='*20)
print(concat_result)

Uscita codice

   v1     v2  v3  v4  v5
0   1     10   0   5   3
1   5    100   1   5   2
2   9   1000   2   5   1
3  13  10000   3   5   0
====================
     v1       v2   v3   v4   v5
0   1.0     10.0  0.0  NaN  NaN
1   5.0    100.0  1.0  NaN  NaN
2   9.0   1000.0  2.0  NaN  NaN
3  13.0  10000.0  3.0  NaN  NaN
0   NaN      NaN  NaN  5.0  3.0
1   NaN      NaN  NaN  5.0  2.0
2   NaN      NaN  NaN  5.0  1.0

È comunque possibile ottenere il primo output (merge) con concat modificando il parametro dell'asse

concat_result = pd.concat([df_left, df_right], sort=False, axis=1)

Osserva il seguente comportamento,

concat_result = pd.concat([df_left, df_right, df_left, df_right], sort=False)

uscite;

     v1       v2   v3   v4   v5
0   1.0     10.0  0.0  NaN  NaN
1   5.0    100.0  1.0  NaN  NaN
2   9.0   1000.0  2.0  NaN  NaN
3  13.0  10000.0  3.0  NaN  NaN
0   NaN      NaN  NaN  5.0  3.0
1   NaN      NaN  NaN  5.0  2.0
2   NaN      NaN  NaN  5.0  1.0
3   NaN      NaN  NaN  5.0  0.0
0   1.0     10.0  0.0  NaN  NaN
1   5.0    100.0  1.0  NaN  NaN
2   9.0   1000.0  2.0  NaN  NaN
3  13.0  10000.0  3.0  NaN  NaN
0   NaN      NaN  NaN  5.0  3.0
1   NaN      NaN  NaN  5.0  2.0
2   NaN      NaN  NaN  5.0  1.0
3   NaN      NaN  NaN  5.0  0.0

, che non è possibile eseguire un'operazione simile con l'unione, poiché consente solo un singolo DataFrame o Series denominato.

merge_result = df_left.merge([df_right, df_left, df_right], left_index=True, right_index=True)

uscite;

TypeError: Can only merge Series or DataFrame objects, a <class 'list'> was passed

Conclusione

Come avrai già notato, input e output potrebbero essere diversi tra "merge" e "concat".

Come ho detto all'inizio, la primissima differenza (principale) è che "merge" esegue un join più strutturato con un insieme di oggetti e parametri ristretti dove come "concat" esegue un join meno rigoroso / più ampio con un insieme più ampio di oggetti e parametri.

Tutto sommato, l'unione è meno tollerante alle modifiche / (l'input) e "concat" è più sciolto / meno sensibile alle modifiche / (l'input). È possibile ottenere "unione" utilizzando "concat", ma non è sempre vero il contrario.

L'operazione "Unisci" utilizza colonne di frame di dati (o nome pd.Seriesdell'oggetto) o indici di riga e poiché utilizza solo quelle entità, esegue l'unione orizzontale di frame di dati o serie e di conseguenza non applica l'operazione verticale.

Se vuoi vedere di più, puoi immergerti un po 'nel codice sorgente;


0

Solo la funzione concat ha il parametro dell'asse. Unisci viene utilizzato per combinare i dataframe fianco a fianco in base ai valori nelle colonne condivise, quindi non è necessario il parametro dell'asse.


-2

per impostazione predefinita:
join è un join sinistro a
livello di colonna pd.merge è un join interno a livello di colonna
pd.concat è un join esterno a livello di riga

pd.concat:
accetta argomenti iterabili. Pertanto, non può accettare DataFrame direttamente (usa [df, df2])
dimensioni di DataFrame devono corrispondere lungo l'asse

Join e pd.merge:
può accettare argomenti DataFrame

Fare clic per vedere l'immagine per capire perché il codice seguente fa la stessa cosa

df1.join(df2)
pd.merge(df1, df2, left_index=True, right_index=True)
pd.concat([df1, df2], axis=1)
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.