【发布时间】:2017-05-22 04:17:54
【问题描述】:
如何为 pandas DataFrame 和原生 Python dict 创建一个 mixin 类,以便可以像嵌套 dict 一样访问 dataframe 列?
从Accessing pandas DataFrame as a nested list 开始,使用df.loc() 函数是访问所需行/列/切片的方法。
但目标是使用与原生 Python dict 相同的语法访问二维数据帧。例如
>>> import pandas as pd
>>> df = pd.DataFrame([['x', 1,2,3,4,5], ['y', 6,7,8,9,10], ['z', 11,12,13,14,15]])
>>> df.columns = ['index', 'a', 'b', 'c', 'd', 'e']
>>> df = df.set_index(['index'])
>>> df
a b c d e
index
x 1 2 3 4 5
y 6 7 8 9 10
z 11 12 13 14 15
>>> df['x']
[1, 2, 3, 4, 5]
>>> df['x']['a']
1
>>> df['x']['a', 'b']
(1, 2)
>>> df['x']['a', 'd', 'c']
(1, 4, 3)
我已经尝试过这样创建一个 mixin 类:
from pandas import DataFrame
class VegeTable(DataFrame, dict):
def __init__(self, *args, **kwargs):
DataFrame.__init__(self, *args, **kwargs)
def __getitem__(self, row_key, column_key):
if type(row_key) != list:
row_key = [row_key]
if type(column_key) != list:
column_key = [column_key]
return df.loc[row_key, column_key]
但我认为缺少一些东西,例如字典键访问不起作用,dict.get 返回一个奇怪的值:
>>> from pandas import DataFrame
>>>
>>>
>>> class VegeTable(DataFrame, dict):
... def __init__(self, *args, **kwargs):
... DataFrame.__init__(self, *args, **kwargs)
... def __getitem__(self, row_key, column_key):
... if type(row_key) != list:
... row_key = [row_key]
... if type(column_key) != list:
... column_key = [column_key]
... return df.loc[row_key, column_key]
...
>>>
>>> vt = VegeTable([['x', 1,2,3,4,5], ['y', 6,7,8,9,10], ['z', 11,12,13,14,15]])
>>> vt.columns = ['index', 'a', 'b', 'c', 'd', 'e']
>>> vt = vt.set_index(['index'])
>>> vt
a b c d e
index
x 1 2 3 4 5
y 6 7 8 9 10
z 11 12 13 14 15
>>> vt['x']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/lib/python2.7/site-packages/pandas/core/frame.py", line 2062, in __getitem__
return self._getitem_column(key)
File "/usr/local/lib/python2.7/site-packages/pandas/core/frame.py", line 2069, in _getitem_column
return self._get_item_cache(key)
File "/usr/local/lib/python2.7/site-packages/pandas/core/generic.py", line 1534, in _get_item_cache
values = self._data.get(item)
File "/usr/local/lib/python2.7/site-packages/pandas/core/internals.py", line 3590, in get
loc = self.items.get_loc(item)
File "/usr/local/lib/python2.7/site-packages/pandas/core/indexes/base.py", line 2395, in get_loc
return self._engine.get_loc(self._maybe_cast_indexer(key))
File "pandas/_libs/index.pyx", line 132, in pandas._libs.index.IndexEngine.get_loc (pandas/_libs/index.c:5239)
File "pandas/_libs/index.pyx", line 154, in pandas._libs.index.IndexEngine.get_loc (pandas/_libs/index.c:5085)
File "pandas/_libs/hashtable_class_helper.pxi", line 1207, in pandas._libs.hashtable.PyObjectHashTable.get_item (pandas/_libs/hashtable.c:20405)
File "pandas/_libs/hashtable_class_helper.pxi", line 1215, in pandas._libs.hashtable.PyObjectHashTable.get_item (pandas/_libs/hashtable.c:20359)
KeyError: 'x'
>>> vt.get(['x'])
>>> vt.get('x')
>>> vt.get('x', 'a')
'a'
>>> vt.get('x', ['a', 'b'])
['a', 'b']
>>> vt.get('x', ['a', 'b'])
如何为 pandas DataFrame 和本机 Python dict 创建一个 mixin 类,以便可以像嵌套 dict 一样访问数据帧列?这可能吗?如果有,怎么做?
【问题讨论】:
-
如果您使用
__getitem__进行行访问,而不是当前列访问,您建议如何进行列访问? -
与访问嵌套字典
defaultdict(dict)的方式相同,即vt[row_ids, column_ids]以及对于行访问,vt[row_ids]。
标签: python pandas dictionary get mixins