我在考虑最近项目中可能由pandas
中的非唯一索引引起的潜在问题,所以我开始玩一些场景来看看会发生什么。在这样做时,我偶然发现了以下奇怪的行为:
In [1]: import pandas as pd
In [2]: pd.version.version
Out[2]: '0.12.0'
In [3]: df1 = pd.DataFrame(range(10), index=[1, 2]*5)
In [4]: df2 = pd.DataFrame(range(10), index=range(5)*2)
In [5]: df1
Out[5]:
0
1 0
2 1
1 2
2 3
1 4
2 5
1 6
2 7
1 8
2 9
In [6]: df2
Out[6]:
0
0 0
1 1
2 2
3 3
4 4
0 5
1 6
2 7
3 8
4 9
如果我将df2
的索引传递给df1
的索引器,我会得到一些意想不到的结果(用箭头表示)
In [7]: df1.ix[df2.index]
Out[7]:
0
0 NaN
1 2.000000e+00
1 4.000000e+00
1 6.000000e+00
1 8.000000e+00
1 1.000000e+00 <---
2 3.000000e+00
2 5.000000e+00
2 7.000000e+00
2 9.000000e+00
2 0.000000e+00 <---
3 NaN
4 NaN
0 NaN
1 8.000000e+00
1 1.000000e+00 <---
1 3.000000e+00 <---
1 5.000000e+00 <---
1 7.000000e+00 <---
2 9.000000e+00
2 3.636673e+17 <---
2 4.020594e+17 <---
2 3.628229e+17 <---
2 2.171412e+18 <---
3 NaN
4 NaN
不仅DataFrame
中没有值,而且每个索引关联的一些值都是错误的/意外的;与1
关联的值应为0,2,4,6和8,与2
关联的值应为1,3,5,7和9.我认为这可能有与DataFrame.ix
接受位置索引或标签有关,但同样的事情发生在DataFrame.loc
In [10]: df1.loc[df2.index]
Out[10]:
0
0 NaN
1 2.000000e+00
1 4.000000e+00
1 6.000000e+00
1 8.000000e+00
1 1.000000e+00
2 3.000000e+00
2 5.000000e+00
2 7.000000e+00
2 9.000000e+00
2 0.000000e+00
3 NaN
4 NaN
0 NaN
1 8.000000e+00
1 1.000000e+00
1 3.000000e+00
1 5.000000e+00
1 7.000000e+00
2 9.000000e+00
2 3.625411e+17
2 3.996824e+17
2 4.009981e+17
2 3.636670e+17
3 NaN
4 NaN
我多次重新运行此方案,并且意外值始终出现在同一位置,但可能是不同的值。为什么会发生这种情况,为什么不提出异常呢?我在文档中找不到解释,这在我工作的32位Windows系统和64位Linux上都会发生
系统在家里。我正在使用numpy 1.8.0
,顺便说一句。
答案 0 :(得分:1)
重复索引的重复索引在0.12中有所突破。这是0.13的结果。您的结果是一些内部例程访问非初始化内存的结果(因此返回的'值'在运行之间可能不一致 - 因此它是一个错误)。
你必须真正考虑你要求大熊猫做什么。
您所说的是根据您提供的df2.index
的值进行查找,并在df1
的索引中找到它们。
值0,3,4
不在df1的索引中,因此它们被标记为nan
(因为它们被指定两次,所以每次都会得到nan
两次)。值1
和2
匹配,每次匹配时都会得到匹配值(并且每次匹配都会得到多个值)。
In [13]: df1.ix[df2.index]
Out[13]:
0
0 NaN
1 0
1 2
1 4
1 6
1 8
2 1
2 3
2 5
2 7
2 9
3 NaN
4 NaN
0 NaN
1 0
1 2
1 4
1 6
1 8
2 1
2 3
2 5
2 7
2 9
3 NaN
4 NaN
[26 rows x 1 columns]
您可能正在寻找这种位置索引。您提供的值是结果的locations
(并且不关心标签)。这适用于0.12和0.13 FYI。
In [14]: df1.iloc[df2.index]
Out[14]:
0
1 0
2 1
1 2
2 3
1 4
1 0
2 1
1 2
2 3
1 4
[10 rows x 1 columns]
重复重复索引非常棘手。如果你有一个替代解决方案,它提供了某些属性(例如索引器的顺序必须保留在输出中,你需要保证匹配所有重复项),我们很乐意听到它。