Menggabungkan string dari beberapa baris menggunakan Pandas groupby


92

Saya ingin menggabungkan beberapa string dalam dataframe berdasarkan groupedby in Pandas.

Ini adalah kode saya sejauh ini:

import pandas as pd
from io import StringIO

data = StringIO("""
"name1","hej","2014-11-01"
"name1","du","2014-11-02"
"name1","aj","2014-12-01"
"name1","oj","2014-12-02"
"name2","fin","2014-11-01"
"name2","katt","2014-11-02"
"name2","mycket","2014-12-01"
"name2","lite","2014-12-01"
""")

# load string as stream into dataframe
df = pd.read_csv(data,header=0, names=["name","text","date"],parse_dates=[2])

# add column with month
df["month"] = df["date"].apply(lambda x: x.month)

Saya ingin hasil akhirnya terlihat seperti ini:

masukkan deskripsi gambar di sini

Saya tidak mengerti bagaimana saya bisa menggunakan groupby dan menerapkan semacam penggabungan string di kolom "teks". Setiap bantuan dihargai!

Jawaban:


160

Anda dapat mengelompokkan berdasarkan kolom 'name'dan 'month', lalu memanggil transformyang akan mengembalikan data yang selaras dengan df asli dan menerapkan lambda di mana kita joinmemasukkan teks:

In [119]:

df['text'] = df[['name','text','month']].groupby(['name','month'])['text'].transform(lambda x: ','.join(x))
df[['name','text','month']].drop_duplicates()
Out[119]:
    name         text  month
0  name1       hej,du     11
2  name1        aj,oj     12
4  name2     fin,katt     11
6  name2  mycket,lite     12

Saya sub df asli dengan melewatkan daftar kolom yang menarik di df[['name','text','month']]sini dan kemudian memanggildrop_duplicates

EDIT sebenarnya saya bisa menelepon applydan kemudian reset_index:

In [124]:

df.groupby(['name','month'])['text'].apply(lambda x: ','.join(x)).reset_index()

Out[124]:
    name  month         text
0  name1     11       hej,du
1  name1     12        aj,oj
2  name2     11     fin,katt
3  name2     12  mycket,lite

memperbarui

yang lambdatidak perlu di sini:

In[38]:
df.groupby(['name','month'])['text'].apply(','.join).reset_index()

Out[38]: 
    name  month         text
0  name1     11           du
1  name1     12        aj,oj
2  name2     11     fin,katt
3  name2     12  mycket,lite

1
Dalam pandas < 1.0, .drop_duplicates()mengabaikan indeks, yang mungkin memberikan hasil yang tidak diharapkan. Anda dapat menghindari ini dengan menggunakan .agg(lambda x: ','.join(x))sebagai pengganti .transform().drop_duplicates().
Matthias Fripp

Rapi dan tidak rumit. Sangat mudah diubah juga
Raghavan vmvs

drop_duplicates()mungkin tidak berfungsi jika Anda tidak menyertakan parameter drop_duplicates(inplace=True)atau hanya menulis ulang baris kode sebagai df = df[['name','text','month']].drop_duplicates()
IAmBotmaker

44

kita bisa mengelompokkan berdasarkan kolom 'nama' dan 'bulan', lalu memanggil fungsi agg () dari objek DataFrame Panda.

Fungsionalitas agregasi yang disediakan oleh fungsi agg () memungkinkan beberapa statistik dihitung per grup dalam satu penghitungan.

df.groupby(['name', 'month'], as_index = False).agg({'text': ' '.join})

masukkan deskripsi gambar di sini


27

Jawaban oleh EdChum memberi Anda banyak fleksibilitas, tetapi jika Anda hanya ingin menggabungkan string ke dalam kolom objek daftar, Anda juga dapat:

output_series = df.groupby(['name','month'])['text'].apply(list)


Sobat, kamu baru saja menghemat banyak waktu. Terima kasih. Ini adalah cara terbaik untuk menyusun daftar kronologis pendaftaran / id pengguna menjadi 'kelompok' yang saya ketahui. Terima kasih sekali lagi.
Alex Fedotov

5

Bagi saya solusi di atas sudah dekat tetapi menambahkan beberapa / n yang tidak diinginkan dan dtype: object, jadi inilah versi yang dimodifikasi:

df.groupby(['name', 'month'])['text'].apply(lambda text: ''.join(text.to_string(index=False))).str.replace('(\\n)', '').reset_index()
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.