Pandas: 不等长Series的布尔索引

6 投票
1 回答
16030 浏览
提问于 2025-04-18 02:50

假设你有两个pandas系列对象,分别叫做A和Matches。Matches里面包含了A的一部分索引,并且里面的值是布尔值(真或假)。那么,怎么才能实现逻辑索引呢?

如果Matches和A的长度是一样的,你可以直接用:

A[Matches] = 5.*Matches

但是如果Matches比A短,就需要这样做:

error: Unalignable boolean Series key provided

编辑 1:根据要求的示例

In [15]: A = pd.Series(range(10))

In [16]: A
Out[16]: 0    0
1    1
2    2
3    3
4    4
5    5
6    6
7    7
8    8
9    9
dtype: int64

In [17]: Matches = (A<3)[:5]

In [18]: Matches
Out[18]: 0     True
1     True
2     True
3    False
4    False
dtype: bool

In [19]: A[Matches] = None
---------------------------------------------------------------------------
IndexingError                             Traceback (most recent call last)
<ipython-input-19-7a04f32ce860> in <module>()
----> 1 A[Matches] = None

C:\Anaconda\lib\site-packages\pandas\core\series.py in __setitem__(self, key, value)
    631 
    632         if _is_bool_indexer(key):
--> 633             key = _check_bool_indexer(self.index, key)
    634             try:
    635                 self.where(~key, value, inplace=True)

C:\Anaconda\lib\site-packages\pandas\core\indexing.py in _check_bool_indexer(ax, key)
   1379         mask = com.isnull(result.values)
   1380         if mask.any():
-> 1381             raise IndexingError('Unalignable boolean Series key provided')
   1382 
   1383         result = result.astype(bool).values

IndexingError: Unalignable boolean Series key provided

In [20]: 

我想要的结果是:

In [16]: A
Out[16]: 0    None
1    None
2    None
3    3
4    4
5    5
6    6
7    7
8    8
9    9
dtype: int64

Matches系列的构造是人为的,仅用于说明。而且在我的情况下,行索引显然不是数字,并且不等于元素的值……

1 个回答

4

好吧,你不能得到你想要的结果,因为 int64 这种数据类型不能包含 None。None 不是一个整数。不过你可以找到一个接近的解决办法:

>>> A = pd.Series(range(10))
>>> Matches = (A<3)[:5]
>>> A[Matches[Matches].index] = None
>>> A
0    None
1    None
2    None
3       3
4       4
5       5
6       6
7       7
8       8
9       9
dtype: object

这个方法有效,因为 Matches[Matches] 会选择那些在 Matches 中为真的元素。

撰写回答