pandas dataframe - 过滤会产生意外错误'无法解决的类型'

时间:2015-03-05 11:48:50

标签: python pandas

以下Python片段给出了一个错误:

df = pandas.DataFrame({'A': ['UBS','UBS','ABB','UBS'], 'B': ['L', 'L', 'L', 'D']})
cols = ['A', 'A', 'B']
df = df[cols]
df = df[df['A'].isin(['UBS']) & (df['B'] != 'D')]    

我得到的错误是unorderable types: str() < int()。我会理解它是否在抱怨重复的列,但为什么它会尝试(并且失败)比较整数和字符串?

如果我用df = df[df['A'].isin(['UBS'])]替换最后一行,我会收到预期的错误消息cannot reindex from a duplicate axis

不可否认,这个例子是设计的(它是真实代码的一个简化示例),如果我交换最后两行代码可以正常工作,但我仍然想了解错误。

1 个答案:

答案 0 :(得分:9)

当Pandas计算

时发生异常
df['A'].isin(['UBS']) & (df['B'] != 'D')

第一个表达式是布尔值的Dataframe,第二个是布尔值的Series。 DataFrame的主轴(列轴)具有索引

Index(['A', 'A'], dtype='object')

而系列的主轴有索引

Int64Index([0, 1, 2, 3], dtype='int64')

Pandas尝试对齐这两个索引,并且作为该过程的一部分,比较索引中的值。在Python2中,字符串和整数是可比较的,在Python3中,这种比较引发了异常。


如果在Python3下运行代码,则回溯错误消息以

结尾
  File "/home/unutbu/.virtualenvs/muffy/lib/python3.4/site-packages/pandas-0.15.2_226_ge1aaf8c-py3.4-linux-x86_64.egg/pandas/core/index.py", line 2005, in _join_monotonic
    join_index, lidx, ridx = self._outer_indexer(sv, ov)
  File "pandas/src/generated.pyx", line 8558, in pandas.algos.outer_join_indexer_object (pandas/algos.c:157918)
TypeError: unorderable types: str() < int()

现在,如果你插入

import pdb
pdb.set_trace()

在引发异常之前进入代码,然后重新运行脚本, 你可以在Python的最后一行设置一个断点,发生异常:

(Pdb) b /home/unutbu/.virtualenvs/muffy/lib/python3.4/site-packages/pandas-0.15.2_226_ge1aaf8c-py3.4-linux-x86_64.egg/pandas/core/index.py:2005
Breakpoint 1 at /home/unutbu/.virtualenvs/muffy/lib/python3.4/site-packages/pandas-0.15.2_226_ge1aaf8c-py3.4-linux-x86_64.egg/pandas/core/index.py:2005
(Pdb) cont
> /home/unutbu/.virtualenvs/muffy/lib/python3.4/site-packages/pandas-0.15.2_226_ge1aaf8c-py3.4-linux-x86_64.egg/pandas/core/index.py(2005)_join_monotonic()
-> join_index, lidx, ridx = self._outer_indexer(sv, ov)

现在您可以检查有问题的变量的值:

(Pdb) p sv
array(['A', 'A'], dtype=object)
(Pdb) p ov
array([0, 1, 2, 3], dtype=object)
(Pdb) q

这表明sv包含字符串,ov包含整数。在Python2中,strint具有可比性 - In CPython any str is greater than any int - 因此pandas/src/generated.pyxlval进行比较时,rval不会引发异常}}:

        elif lval < rval:
            count += 1
            i += 1

但是in Python3, strs and ints are no longer comparable。因此,Python3中早于Python2引发异常。在Python2中,错误随后出现并引发

cannot reindex from a duplicate axis

您在df = df[df['A'].isin(['UBS'])]时遇到同样的错误,而不是unorderable types错误,因为此处没有&