我已经读过关于切割机的医生上百万次了,但是我从来没有读过它,所以我仍然在努力弄清楚如何使用loc来分割一个DataFrame和一个MultiIndex。
我将从DataFrame从这就是答案开始
value
first second third fourth
A0 B0 C1 D0 2
D1 3
C2 D0 6
D1 7
B1 C1 D0 10
D1 11
C2 D0 14
D1 15
A1 B0 C1 D0 18
D1 19
C2 D0 22
D1 23
B1 C1 D0 26
D1 27
C2 D0 30
D1 31
A2 B0 C1 D0 34
D1 35
C2 D0 38
D1 39
B1 C1 D0 42
D1 43
C2 D0 46
D1 47
A3 B0 C1 D0 50
D1 51
C2 D0 54
D1 55
B1 C1 D0 58
D1 59
C2 D0 62
D1 63要选择A0和C1值,我可以这样做:
In [26]: df.loc['A0', :, 'C1', :]
Out[26]:
value
first second third fourth
A0 B0 C1 D0 2
D1 3
B1 C1 D0 10
D1 11它还可以从三个级别进行选择,甚至可以使用元组:
In [28]: df.loc['A0', :, ('C1', 'C2'), 'D1']
Out[28]:
value
first second third fourth
A0 B0 C1 D1 3
C2 D1 5
B1 C1 D1 11
C2 D1 13到目前为止,直觉和聪明。
那么为什么我不能从第一个索引级别中选择所有的值呢?
In [30]: df.loc[:, :, 'C1', :]
---------------------------------------------------------------------------
IndexingError Traceback (most recent call last)
<ipython-input-30-57b56108d941> in <module>()
----> 1 df.loc[:, :, 'C1', :]
/usr/local/lib/python2.7/dist-packages/pandas/core/indexing.pyc in __getitem__(self, key)
1176 def __getitem__(self, key):
1177 if type(key) is tuple:
-> 1178 return self._getitem_tuple(key)
1179 else:
1180 return self._getitem_axis(key, axis=0)
/usr/local/lib/python2.7/dist-packages/pandas/core/indexing.pyc in _getitem_tuple(self, tup)
694
695 # no multi-index, so validate all of the indexers
--> 696 self._has_valid_tuple(tup)
697
698 # ugly hack for GH #836
/usr/local/lib/python2.7/dist-packages/pandas/core/indexing.pyc in _has_valid_tuple(self, key)
125 for i, k in enumerate(key):
126 if i >= self.obj.ndim:
--> 127 raise IndexingError('Too many indexers')
128 if not self._has_valid_type(k, i):
129 raise ValueError("Location based indexing can only have [%s] "
IndexingError: Too many indexers这肯定不是有意的行为?
注意:我知道这在df.xs('C1', level='third')中是可能的,但是当前的.loc行为似乎不一致。
发布于 2016-07-01 20:20:06
这不起作用的原因是需要指定索引的轴(在http://pandas.pydata.org/pandas-docs/stable/advanced.html中提到)。解决您的问题的另一种解决方案就是简单地这样做:
df.loc(axis=0)[:, :, 'C1', :]有时,当指数相似或包含相似值时,熊猫会感到困惑。如果您要有一个名为“C1”的列,那么您也需要在这种切片/选择风格下这样做。
发布于 2015-06-11 13:06:10
为了安全起见(从某种意义上说,这在所有情况下都是有效的),您需要同时索引行索引和列,为此您可以使用pd.IndexSlice轻松地做到这一点:
In [26]: idx = pd.IndexSlice
In [27]: df.loc[idx[:, :, 'C1', :],:]
Out[27]:
value
first second third fourth
A0 B0 C1 D0 2
D1 3
B1 C1 D0 10
D1 11
A1 B0 C1 D0 18
D1 19
B1 C1 D0 26
D1 27
A2 B0 C1 D0 34
D1 35
B1 C1 D0 42
D1 43
A3 B0 C1 D0 50
D1 51
B1 C1 D0 58
D1 59在这里,idx[:, :, 'C1', :]是一种更容易编写[slice(None), slice(None),'C1', slice(None)]的方法。您也可以使用更短一些的pd.IndexSlice,而不是np.s_。
其他人工作的原因,我不完全确定。但请参阅文档中的注释:http://pandas.pydata.org/pandas-docs/stable/advanced.html#using-slicers (第一个红色警告框),其中声明:
您应该在
.loc说明符中指定所有轴,这意味着索引和列的索引器。它们是一些模棱两可的情况,传递的索引器可能被错误地解释为两个轴的索引,而不是行的MuliIndex。
https://stackoverflow.com/questions/30781037
复制相似问题