我目前正在尝试了解有关Pandas的更多信息,并且正在查看文档中的Boolean Indexing部分。
在给出的示例中,注意到对于DataFrame
In[439]: df2 = pd.DataFrame({'a' : ['one', 'one', 'two', 'three', 'two', 'one', 'six'],
'b' : ['x', 'y', 'y', 'x', 'y', 'x', 'x'],
'c' : np.random.randn(7)})
In[440]: df2
Out[440]:
a b c
0 one x -0.858441
1 one y 0.643366
2 two y -0.862198
3 three x -0.408981
4 two y 1.137740
5 one x 0.829057
6 six x -1.251656
使用系列的map
方法
In [441]: criterion = df2['a'].map(lambda x: x.startswith('t'))
In [442]: df2[criterion]
Out[442]:
a b c
2 two y 0.041290
3 three x 0.361719
4 two y -0.238075
比同等列表理解
更快In [443]: df2[[x.startswith('t') for x in df2['a']]]
Out[443]:
a b c
2 two y 0.041290
3 three x 0.361719
4 two y -0.238075
现在针对这种情况,我会使用文档中没有提到的df2[df2.a.str.startswith('t')]
,所以我想对这些方法进行基准测试。
小编基准
%timeit df2[df2.a.str.startswith('t')]
1000 loops, best of 3: 880 µs per loop
%timeit df2[df2['a'].map(lambda x: x.startswith('t'))]
1000 loops, best of 3: 783 µs per loop
%timeit df2[[x.startswith('t') for x in df2['a']]]
1000 loops, best of 3: 572 µs per loop
令人惊讶的是,列表理解方法似乎是最快的!所以我尝试使DataFrame 更多更大并再次进行基准测试。
In[444]: df2 = pd.DataFrame({'a' : ['one', 'one', 'two', 'three', 'two', 'one', 'six']*1000000,
'b' : ['x', 'y', 'y', 'x', 'y', 'x', 'x']*1000000,
'c' : np.random.randn(7*1000000)})
Big Series基准
%timeit df2[df2.a.str.startswith('t')]
1 loop, best of 3: 5.89 s per loop
%timeit df2[df2['a'].map(lambda x: x.startswith('t'))]
1 loop, best of 3: 5.73 s per loop
%timeit df2[[x.startswith('t') for x in df2['a']]]
1 loop, best of 3: 3.95 s per loop
列表理解似乎仍然是最快的,而且大型系列的差异更加明显。
系列的map
方法通常实际上比布尔索引的列表推导更快吗?为什么列表理解方法在这里看起来实际上更快并且与documentation section相矛盾?
我的基准测试方法或测试中可能存在错误,我很清楚,对于更复杂的标准(甚至是简单的标准),前两种方法中的一种很多更好看看并实施,但我的问题只是表现。
注意:我使用的是Pandas版本0.18.1
答案 0 :(得分:2)
IMO它不是关于布尔索引 - 它是关于使用字符串系列:
In [204]: %timeit df.a.str.startswith('t')
10 loops, best of 3: 75.7 ms per loop
In [205]: %timeit df['a'].map(lambda x: x.startswith('t'))
10 loops, best of 3: 76.5 ms per loop
In [206]: %timeit [x.startswith('t') for x in df['a']]
10 loops, best of 3: 39.7 ms per loop
In [209]: %timeit [df.a.str[0] == 't']
10 loops, best of 3: 85.2 ms per loop
DF形状:70.000 x 3
In [207]: df.shape
Out[207]: (70000, 3)
使用string
系列时,列表理解通常会更快。
PS我在本例中使用Pandas版本0.19.2