Pandas处理“大”数据的一些技巧

Pandas处理“大”数据的一些技巧

实习定下来下的空档期,抽空参加了一些大数据竞赛,pandas用的比较多,所以这里汇总下pandas的一些使用心得和总结一些遇到过的问题吧。

数据读取慢(文件很大)

  • pandas里面的read类函数都是单线程实现的,这里可以考虑使用分布式多线程版本的pandas: modin.pandas 更换import就可以实现四倍读写

  • 第一读写完的时候就把数据转换为.h5格式的文件,既可以压缩又可以提高读取效率。要注意的是,转成为h5文件,最好保证每列数据类型的一致,这样才能使用c接口读取提高效率,否则将默认使用python接口

  • 设置分快读取,最后合并

import pandas as pd
res=[]
for dfs in pd.read_csv('data.csv',chunksize=1000,iterator=True):
	do(dfs)#处理子块
	res.append(dfs)
pd.concat(res,axis=0)# 最后拼接好结果

# chunksize 设置读取块的大小(行),最后一次可能不满1000
  • 只读取部分列,指定参数usecols = [0,1,2,3],类似切片操作即选择第0-3列

数据处理慢

  • pandas 的apply函数是单线程的,所以可以考虑用joblib库中的Parallel, delayed实现多进程或多线程(这里使用sklearn中的joblib,因为它报错信息更友好,方便debug,而且优化很好)
import pandas as pd
from sklearn.externals.joblib import Parallel, delayed
def apply_parallel(df, func, cpu_n=16):
    """利用 Parallel 和 delayed 函数实现并行运算,思路是把Dataframe分割喂给包含apply的函数
       @params df:        需要apply的Dataframe
       @params func:      包含apply的函数,(不是apply的参数那个函数),需自己定义,
       @params cpu_n:         cpu_n为进程数
       @return Dataframe: apply参数函数得到的Dataframe
   """
    df_length=len(df)
    cpu_n=16
    d=df_length//cpu_n
    sp=[]
    for i in range(0, cpu_n-1):
        sp.append(range(i*d,(i+1)*d))
    sp.append(range((cpu_n-1)*d,df_length))
    results = Parallel(n_jobs=cpu_n)(delayed(func)(df.iloc[spl]) for spl in sp)
    #results = Parallel(backend="threading",n_jobs=cpu_n)(delayed(func)(df.iloc[spl]) for spl in sp) 即可设置多线程
    return pd.concat(results)
def do_some_to__df(df):
	#这里传入的是切成块的dataframe,所以在里面再进行apply就行
	df.apply(...)
	return df
df=apply_parallel(df,do_some_to__df, cpu_n=16)

模型训练慢

  • 特征筛选
  • 请使用GPU版的模型(lightgbm_gpu)啥的

最终级方法(堆硬件)

  • 数据放固态
  • 加大内存,把数据放内存盘

你可能感兴趣的:(useful,tools)