Apakah mungkin untuk menambahkan beberapa meta-informasi / metadata ke DataFrame pandas?
Misalnya nama instrumen yang digunakan untuk mengukur data, instrumen yang bertanggung jawab, dll.
Salah satu solusinya adalah membuat kolom dengan informasi tersebut, tetapi tampaknya sia-sia untuk menyimpan satu informasi di setiap baris!
Jawaban:
Tentu, seperti kebanyakan objek Python, Anda dapat melampirkan atribut baru ke
pandas.DataFrame
:import pandas as pd df = pd.DataFrame([]) df.instrument_name = 'Binky'
Catatan, bagaimanapun, bahwa sementara Anda dapat melampirkan atribut untuk DataFrame, operasi dilakukan pada DataFrame (seperti
groupby
,pivot
,join
atauloc
hanya beberapa nama) dapat kembali DataFrame baru tanpa metadata terpasang. Panda belum memiliki metode yang kuat untuk menyebarkan metadata yang dilampirkan ke DataFrames .Menjaga metadata dalam file dimungkinkan. Anda dapat menemukan contoh cara menyimpan metadata dalam file HDF5 di sini .
sumber
store = pd.HDFStore(...)
, maka atribut dapat disimpan denganstore.root._v_attrs.key = value
.df = pd.DataFrame(); df.meta = {}
menghasilkanUserWarning: Pandas doesn't allow columns to be created via a new attribute name - see https://pandas.pydata.org/pandas-docs/stable/indexing.html#attribute-access
). (Tidak ada peringatan yang diberikan jika atribut telah dibuat seperti didf = pd.DataFrame(); df.meta = ''; df.meta = {}
).Saya sendiri mengalami masalah ini. Mulai pandas 0.13, DataFrames memiliki atribut _metadata yang tetap ada melalui fungsi yang mengembalikan DataFrames baru. Juga tampaknya bertahan serialisasi dengan baik (saya hanya mencoba json, tapi saya membayangkan hdf tercakup juga).
sumber
_metadata
bukan bagian dari API publik, jadi saya sangat menyarankan agar Anda tidak mengandalkan fungsi ini..attrs
merupakan bagian dari xray API)_metadata
sebenarnya adalah atribut kelas, bukan atribut instance. JadiDataFrame
instance baru diturunkan dari yang sebelumnya, selama modul tetap dimuat. Jangan gunakan_metadata
untuk apapun. 1 untukxarray
!Tidak juga. Meskipun Anda bisa menambahkan atribut yang berisi metadata ke kelas DataFrame seperti yang @unutbu sebutkan, banyak metode DataFrame mengembalikan DataFrame baru, sehingga data meta Anda akan hilang. Jika Anda perlu memanipulasi dataframe Anda, maka opsi terbaik adalah menggabungkan metadata dan DataFrame Anda di kelas lain. Lihat diskusi ini di GitHub: https://github.com/pydata/pandas/issues/2485
Saat ini ada permintaan tarik terbuka untuk menambahkan objek MetaDataFrame, yang akan mendukung metadata dengan lebih baik.
sumber
Mulai dari panda 1.0, mungkin sebelumnya, sekarang ada
Dataframe.attrs
properti. Ini eksperimental, tetapi ini mungkin yang Anda inginkan di masa mendatang. Sebagai contoh:import pandas as pd df = pd.DataFrame([]) df.attrs['instrument_name'] = 'Binky'
Temukan di dokumen di sini .
Mencoba ini dengan
to_parquet
dan kemudianfrom_parquet
, tampaknya tidak bertahan, jadi pastikan Anda memeriksanya dengan kasus penggunaan Anda.sumber
dataclass
untuk metadata dan kemudian subclassingDataFrame
memiliki metode melakukan load / dumping seperti pada posting yang Anda bagikan bisa menjadi solusi yang bagus.Jawaban teratas dari melampirkan atribut arbitrer ke objek DataFrame adalah baik, tetapi jika Anda menggunakan kamus, daftar, atau tuple, ini akan mengeluarkan kesalahan "Pandas tidak mengizinkan kolom dibuat melalui nama atribut baru". Solusi berikut berfungsi untuk menyimpan atribut arbitrer.
from types import SimpleNamespace df = pd.DataFrame() df.meta = SimpleNamespace() df.meta.foo = [1,2,3]
sumber
pd.DataFrame._metadata += ["meta"]
. Perhatikan bahwa bagian ini adalah atribut Pandas, bukan atribut dataframe spesifik Andadf.meta
memicu peringatan bahwa Pandas tidak mengizinkan kolom baru dibuat dengan cara ini.df.meta
merupakan SimpleNamespace. Panda tidak akan mencoba dan membangun kolom darinya.Seperti yang disebutkan dalam jawaban dan komentar lain,
_metadata
ini bukan bagian dari API publik, jadi jelas bukan ide yang baik untuk menggunakannya dalam lingkungan produksi. Tetapi Anda mungkin masih ingin menggunakannya dalam pembuatan prototipe penelitian dan menggantinya jika berhenti berfungsi. Dan sekarang ini bekerja dengangroupby
/apply
, yang sangat membantu. Ini adalah contoh (yang tidak dapat saya temukan di jawaban lain):df = pd.DataFrame([1, 2, 2, 3, 3], columns=['val']) df.my_attribute = "my_value" df._metadata.append('my_attribute') df.groupby('val').apply(lambda group: group.my_attribute)
Keluaran:
val 1 my_value 2 my_value 3 my_value dtype: object
sumber
Sangat terlambat untuk ini, saya pikir ini mungkin berguna jika Anda memerlukan metadata untuk bertahan selama I / O. Ada paket yang relatif baru bernama h5io yang telah saya gunakan untuk mencapai ini.
Seharusnya Anda dapat melakukan baca / tulis cepat dari HDF5 untuk beberapa format umum, salah satunya adalah kerangka data. Jadi Anda bisa, misalnya, meletakkan kerangka data di kamus dan memasukkan metadata sebagai bidang di kamus. Misalnya:
save_dict = dict(data=my_df, name='chris', record_date='1/1/2016') h5io.write_hdf5('path/to/file.hdf5', save_dict) in_data = h5io.read_hdf5('path/to/file.hdf5') df = in_data['data'] name = in_data['name'] etc...
Pilihan lain adalah melihat ke dalam proyek seperti xray , yang lebih kompleks dalam beberapa hal, tapi menurut saya itu memungkinkan Anda menggunakan metadata dan cukup mudah untuk diubah menjadi DataFrame.
sumber
Seperti yang disebutkan oleh @choldgraf, saya telah menemukan xarray sebagai alat yang sangat baik untuk melampirkan metadata ketika membandingkan data dan memplot hasil antara beberapa kerangka data.
Dalam pekerjaan saya, kami sering membandingkan hasil dari beberapa revisi firmware dan skenario pengujian yang berbeda, menambahkan informasi ini sesederhana ini:
df = pd.read_csv(meaningless_test) metadata = {'fw': foo, 'test_name': bar, 'scenario': sc_01} ds = xr.Dataset.from_dataframe(df) ds.attrs = metadata
sumber
Saya telah mencari solusi dan menemukan bahwa bingkai panda memiliki properti
attrs
pd.DataFrame().attrs.update({'your_attribute' : 'value'}) frame.attrs['your_attribute']
Atribut ini akan selalu menempel pada bingkai Anda setiap kali Anda melewatinya!
sumber
Saya mengalami masalah yang sama dan menggunakan solusi untuk membuat DF baru yang lebih kecil dari kamus dengan metadata:
meta = {"name": "Sample Dataframe", "Created": "19/07/2019"} dfMeta = pd.DataFrame.from_dict(meta, orient='index')
DfMeta ini kemudian dapat disimpan bersama DF asli Anda dalam acar dll
Lihat Menyimpan dan memuat banyak objek dalam file acar? (Jawaban Lutz) untuk jawaban luar biasa tentang menyimpan dan mengambil beberapa kerangka data menggunakan acar
sumber