创建大型Pandas数据框:预分配 vs 追加 vs 连接
创建大型Pandas数据框:预分配 vs 追加 vs 连接
我对在Pandas中按块构建大型数据框时的性能感到困惑。在NumPy中,我们(几乎)总是通过预先分配一个大的空数组,然后填充值来获得更好的性能。据我所知,这是因为NumPy一次性获取所有需要的内存,而不是每个“append”操作都重新分配内存。
在Pandas中,我似乎通过使用“df = df.append(temp)”模式获得更好的性能。
以下是一个计时的示例。Timer类的定义如下。正如您所看到的,与使用“append”相比,预先分配大约慢10倍!使用np.empty值的预先分配数据框的适当dtype可以很好地解决问题,但是“append”方法仍然是最快的。
我使用了Huy Nguyen提供的一个不错的计时器:
# credit: http://www.huyng.com/posts/python-performance-analysis/
import time
class Timer(object):
def __init__(self, verbose=False):
self.verbose = verbose
def __enter__(self):
self.start = time.clock()
return self
def __exit__(self, *args):
self.end = time.clock()
self.secs = self.end - self.start
self.msecs = self.secs * 1000 # millisecs
if self.verbose:
print 'elapsed time: %f ms' % self.msecs
如果您还在继续阅读,我有两个问题:
1)为什么“append”方法更快?(注意:对于非常小的数据框,即n_rows = 40,它实际上更慢)。
2)构建大型数据框的最有效方法是什么?(在我的案例中,这些块都是大型的CSV文件)。
感谢您的帮助!
编辑1:
在我的实际项目中,列具有不同的数据类型。因此,我不能使用“pd.DataFrame(....dtype=some_type)”的技巧来改善预分配的性能,正如BrenBarn的建议所述。dtype参数强制所有列具有相同的数据类型[参考问题4464]。
我在代码中的method2()函数中添加了一些行,逐列更改数据类型以匹配输入数据框。这个操作是昂贵的,并抵消了在写入行块时具有适当数据类型的好处。
编辑2:尝试使用占位符数组“np.empty(...dtype=some_type)”预先分配数据框,根据Joris的建议。