如何使用dask快速访问数据的子集?

时间:2016-12-01 23:45:02

标签: python dask

我喜欢大熊猫的一个主要原因是它容易在子集中居住,例如df[df.sample.isin(['a', 'c', 'p'])]df[df.age < 35]。 dask数据框是否适合(优化)这个?我所看到的教程都集中在全列操作上。

我的具体应用是(数千个命名的GCMS样本)x(每个样本约20000个时间点)x(500 m / z通道)x(强度),我正在寻找最快的拉动工具子集,例如

df[df.sample.isin([...]) & df.rt.lt(800) & df.rt.gt(600) & df.mz.isin(...)]

如果dask是一个不错的选择,那么我会很感激如何最好地构建它。

我尝试了什么

到目前为止,我尝试将每个样本转换为pandas数据框,看起来像是

                  smp     rt       14       15       16       17       18  
0  160602_JK_OFCmix:1  271.0  64088.0   9976.0  26848.0  23928.0  89600.0   
1  160602_JK_OFCmix:1  271.1  65472.0  10880.0  28328.0  24808.0  91840.0   
2  160602_JK_OFCmix:1  271.2  64528.0  10232.0  27672.0  25464.0  90624.0   
3  160602_JK_OFCmix:1  271.3  63424.0  10272.0  27600.0  25064.0  90176.0   
4  160602_JK_OFCmix:1  271.4  64816.0  10640.0  27592.0  24896.0  90624.0  

(&#39; smp&#39;是样本名称,&#39; rt&#39;是保留时间,14,15,... 500是m / z频道),使用zlib保存到hdf,级别= 1,然后用

创建dask数据帧
ddf = dd.read_hdf(*.hdf5, key='/*', chunksize=100000, lock=False)

df = ddf[ddf.smp.isin([...a couple of samples...]).compute()ddf['57'].mean().compute()慢100倍。

(注意:这是dask.set_options(get=dask.multiprocessing.get)

1 个答案:

答案 0 :(得分:1)

您的dask.dataframe由HDF文件支持,因此每次执行任何操作时,您都要从磁盘读取数据。如果您的数据不适合内存,但如果您的数据确实适合内存,则会很浪费。

如果您的数据适合内存

相反,如果您的数据适合内存,请尝试从Pandas数据帧支持您的dask.dataframe:

# ddf = dd.from_hdf(...)
ddf = dd.from_pandas(df, npartitions=20)

我希望您能够从线程或分布式调度程序中看到更好的性能:http://dask.pydata.org/en/latest/scheduler-choice.html

如果您的数据不适合内存

尝试通过指定要在read_hdf调用中读取的一组列来减少必须读取的字节数

df = dd.read_hdf(..., columns=['57'])

或者,更好的是,使用可以高效加载单个列的数据存储。你可以尝试像羽毛或镶木地板这样的东西,尽管两者都处于早期阶段:

我怀疑,如果你小心避免一次性阅读所有列,你可能只使用Pandas而不是使用Dask.dataframe。