get_dummies python内存错误

Due*_*ieb 15 python pandas

我遇到了一个有400,000行和300个变量的数据集的问题.我必须为具有3,000多个不同项目的分类变量获取虚拟变量.最后,我想得到一个包含3,300个变量或特征的数据集,以便我可以训练一个RandomForest模型.

这是我试图做的:

 df = pd.concat([df, pd.get_dummies(df['itemID'],prefix = 'itemID_')], axis=1)
Run Code Online (Sandbox Code Playgroud)

当我这样做时,我总会得到一个内存错误.我可以拥有的变量数量是否有限制?

如果我只用前1000行(有374个不同的类别)那样做,它就可以了.

有没有人能解决我的问题?我正在使用的计算机有8 GB的内存.

Joh*_*hnE 28

更新:从版本0.19.0开始,get_dummies返回一个8位整数而不是64位浮点数,这将在许多情况下解决此问题,并使as_type下面的解决方案不必要.请参阅: get_dummies - pandas 0.19.0

但在其他情况下,sparse下面描述的选项可能仍然有用.

原答案: 这里有几种尝试的可能性.两者都会大幅减少数据帧的内存占用,但您以后仍可能遇到内存问题.这很难预测,你只需要尝试.

(注意我正在简化info()下面的输出)

df = pd.DataFrame({ 'itemID': np.random.randint(1,4,100) })

pd.concat([df, pd.get_dummies(df['itemID'],prefix = 'itemID_')], axis=1).info()

itemID       100 non-null int32
itemID__1    100 non-null float64
itemID__2    100 non-null float64
itemID__3    100 non-null float64

memory usage: 3.5 KB
Run Code Online (Sandbox Code Playgroud)

这是我们的基线.每个虚拟列占用800个字节,因为样本数据有100行,并且get_dummies默认显示为float64(8个字节).这似乎是一种不必要的低效方式来存储虚拟对象,因为你可以使用它做一点点,但可能有一些我不知道的原因.

所以,首先尝试,只需更改为一个字节的整数(这似乎不是一个选项,get_dummies所以它必须作为转换完成astype(np.int8).

pd.concat([df, pd.get_dummies(df['itemID'],prefix = 'itemID_').astype(np.int8)], 
                              axis=1).info()

itemID       100 non-null int32
itemID__1    100 non-null int8
itemID__2    100 non-null int8
itemID__3    100 non-null int8

memory usage: 1.5 KB
Run Code Online (Sandbox Code Playgroud)

现在,每个虚拟列占用内存的1/8.

或者,您可以使用sparse选项get_dummies.

pd.concat([df, pd.get_dummies(df['itemID'],prefix = 'itemID_',sparse=True)], 
                              axis=1).info()

itemID       100 non-null int32
itemID__1    100 non-null float64
itemID__2    100 non-null float64
itemID__3    100 non-null float64

memory usage: 2.0 KB
Run Code Online (Sandbox Code Playgroud)

相当可观的节省.在info()输出有些隐藏的储蓄正在发生的方式,但你可以看看内存使用的价值,看到总储蓄.

其中哪些在实践中会更好地取决于您的数据,所以您只需要尝试一下(或者甚至可以将它们组合起来).

  • 非常感谢。我将数据类型更改为整数并且它有效! (3认同)