Kedua contoh di bawah ini gagal dengan kesalahan yang sama
df = pd.DataFrame(index=[0, 1, 2], columns=['a', 'b'])
df.loc[0, 'a'] = dict(x=2)
df.iloc[0, 0] = dict(x=2)
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
<ipython-input-282-62f3ee5ff885> in <module>()
1 # file_map.loc[file_no, 'Q_step_length'] = dict(a=1)
2 df = pd.DataFrame(index=[0, 1, 2], columns=['a', 'b'])
----> 3 df.iloc[0, 0] = dict(x=2)
4 df['a'] = df['a'].apply(lambda x: x[0] if not pd.isnull(x) else x)
5 df
...\lib\site-packages\pandas\core\indexing.py in __setitem__(self, key, value)
177 key = com._apply_if_callable(key, self.obj)
178 indexer = self._get_setitem_indexer(key)
--> 179 self._setitem_with_indexer(indexer, value)
180
181 def _has_valid_type(self, k, axis):
...\lib\site-packages\pandas\core\indexing.py in _setitem_with_indexer(self, indexer, value)
603
604 if isinstance(value, (ABCSeries, dict)):
--> 605 value = self._align_series(indexer, Series(value))
606
607 elif isinstance(value, ABCDataFrame):
...\lib\site-packages\pandas\core\indexing.py in _align_series(self, indexer, ser, multiindex_indexer)
743 return ser.reindex(ax)._values
744
--> 745 raise ValueError('Incompatible indexer with Series')
746
747 def _align_frame(self, indexer, df):
ValueError: Incompatible indexer with Series
Ini berfungsi, tetapi menempatkan daftar ke dalam kerangka data
df[0, 'a'] = [dict(x=2)]
Dimungkinkan untuk mendapatkan dict secara langsung dalam kerangka data dengan menggunakan konstruksi yang sangat tidak elegan seperti ini:
df['a'] = df['a'].apply(lambda x: x[0] if not pd.isnull(x) else x)
Karena dimungkinkan untuk menyimpan dict dalam kerangka data, mencoba tugas seperti di atas tidak boleh gagal. Saya sadar bahwa df.loc[...] = dict(...) akan menetapkan nilai dalam dict ke kolom yang sesuai jika ada (apakah itu didokumentasikan?) dan memiliki masalah sendiri tetapi perilaku ini seharusnya tidak berlaku saat mengakses satu lokasi kerangka data
Kerangka data dengan dict di dalam lokasi yang ditentukan.
pd.show_versions()
komit: Tidak ada
python: 3.5.4.final.0
python-bit: 64
OS: Windows
Rilis OS: 10
mesin: AMD64
prosesor: Intel64 Family 6 Model 58 Stepping 9, GenuineIntel
urutan byte: sedikit
LC_ALL: Tidak ada
LANG: Tidak ada
LOKAL: Tidak ada. Tidak ada
panda: 0.20.3
pytest: Tidak ada
pip: 9.0.1
setuptools: 36.5.0
Siton: 0,26
numpy: 1.13.1
sip: 0.19.1
xarray: Tidak ada
IPython: 6.1.0
sphinx: Tidak ada
kue: 0.4.1
dateutil: 2.6.1
pytz: 2017.2
blok: Tidak ada
kemacetan: Tidak ada
tabel: Tidak ada
numexpr: Tidak ada
bulu: Tidak ada
matplotlib: 2.0.2
openpyxl: Tidak ada
xlrd: Tidak ada
xlwt: Tidak ada
xlsxpenulis: Tidak ada
lxml: Tidak ada
bs4: Tidak ada
html5lib: 0.9999999
sqlalchemy: Tidak ada
pymysql: Tidak ada
psycopg2: Tidak ada
jinja2: 2.9.6
s3fs: Tidak ada
pandas_gbq: Tidak ada
pandas_datareader: Tidak ada
ini cukup non-idiomatik, dan Anda cukup banyak sendiri di sini. anda bisa melakukannya hanya dengan menggunakan daftar/Tuple di sekitarnya
In [14]: df.loc[0, 'a'] = [dict(x=2)]
In [15]: df
Out[15]:
a b
0 [{'x': 2}] NaN
1 NaN NaN
2 NaN NaN
Mengalami masalah yang sama, memiliki dua pemikiran:
Menyimpan dict dalam DataFrame tidak biasa, tetapi ada kasus yang valid di mana perangkat lunak mungkin menggunakan Pandas sebagai cara untuk mewakili dan memanipulasi data gaya kunci/nilai arbitrer di mana data diindeks dengan cara yang masuk akal untuk representasi panel.
Perilaku pengindeksan berbasis lokasi akan memperbarui kolom berdasarkan kunci/nilai kamus yang disediakan mengejutkan saya. Ini adalah fitur kenyamanan keren yang masuk akal ketika kolom eksplisit tidak direferensikan. Misalnya, saat memberikan:
df.loc[row, :] = dict(key1=value1, key2=value2)
Masuk akal bahwa kunci kamus dapat ditulis sebagai kolom dan df.loc[row, key1] == value1
. Namun, saat memberikan indeks kolom eksplisit, menyimpulkan kolom target dari kamus yang disediakan adalah (bagi saya) kontra-intuitif. Jika saya malah menyediakan:
df.loc[row, col] = dict(key=value)
Saya secara eksplisit menunjukkan bahwa saya ingin menyimpan seluruh nilai di kolom col
, dan saya berharap kamus dimasukkan apa adanya.
Bagaimanapun, saya setuju dengan @jreback bahwa ini agak non-idiomatik TAPI saya bersimpati dengan masalah asli yang diangkat oleh @andreas-thomik. Saya mengalami masalah ketika mencoba menyimpan dict ke elemen kerangka data menggunakan sintaks ini masuk akal untuk masalah khusus yang saya hadapi, jadi dia tidak sepenuhnya sendiri dengan permintaan ini.
@aaclayton ini terkait dengan #18955 . Kami dapat/harus menyelidiki mendukung pengaturan skalar dict dengan lebih baik (dan iterable lainnya). Ini agak rumit.
Komentar yang paling membantu
Mengalami masalah yang sama, memiliki dua pemikiran:
Menyimpan dict dalam DataFrame tidak biasa, tetapi ada kasus yang valid di mana perangkat lunak mungkin menggunakan Pandas sebagai cara untuk mewakili dan memanipulasi data gaya kunci/nilai arbitrer di mana data diindeks dengan cara yang masuk akal untuk representasi panel.
Perilaku pengindeksan berbasis lokasi akan memperbarui kolom berdasarkan kunci/nilai kamus yang disediakan mengejutkan saya. Ini adalah fitur kenyamanan keren yang masuk akal ketika kolom eksplisit tidak direferensikan. Misalnya, saat memberikan:
df.loc[row, :] = dict(key1=value1, key2=value2)
Masuk akal bahwa kunci kamus dapat ditulis sebagai kolom dan
df.loc[row, key1] == value1
. Namun, saat memberikan indeks kolom eksplisit, menyimpulkan kolom target dari kamus yang disediakan adalah (bagi saya) kontra-intuitif. Jika saya malah menyediakan:df.loc[row, col] = dict(key=value)
Saya secara eksplisit menunjukkan bahwa saya ingin menyimpan seluruh nilai di kolom
col
, dan saya berharap kamus dimasukkan apa adanya.Bagaimanapun, saya setuju dengan @jreback bahwa ini agak non-idiomatik TAPI saya bersimpati dengan masalah asli yang diangkat oleh @andreas-thomik. Saya mengalami masalah ketika mencoba menyimpan dict ke elemen kerangka data menggunakan sintaks ini masuk akal untuk masalah khusus yang saya hadapi, jadi dia tidak sepenuhnya sendiri dengan permintaan ini.