将大熊猫间隔转换为字符串(然后再次转换)

时间:2019-08-26 07:54:38

标签: python pandas random-forest binning discretization

我是Python的新手,正在尝试准备一些数据来训练RandomForest。由于各种原因,我们希望数据是离散的,因此需要离散一些连续变量。我在熊猫中发现了qcut,这似乎可以满足我的要求-我可以设置多个bin,它会将变量离散化为这么多个bin,试图将每个bin中的计数保持不变。

但是,pandas.qcut的输出是一个间隔列表,并且scikit-learn中的RandomForest分类器需要一个字符串。我发现可以使用.astype(str)将间隔转换为字符串。这是我正在做的简单示例:

import pandas as pd
from random import sample

vals = sample(range(0,100), 100)
cuts = pd.qcut(vals, q=5)
str_cuts = pd.qcut(vals, q=5).astype(str)

然后str_cuts是传递到随机森林中的变量之一。

但是,此系统的目的是训练RandomForest,将其保存到文件中,然后允许某人稍后加载它并获得新的测试实例的分类,而该分类在训练时不可用。 。并且由于分类器是针对离散化数据进行训练的,因此在使用新测试实例之前,需要对其进行离散化。因此,我想做的是在一个新实例中读取,对其应用已建立的离散化方案,将其转换为字符串并通过随机森林运行它。但是,我一直挂在“应用离散化方案”的最佳方法上。

有一种简单的方法可以解决这个问题吗?我假设没有直接将字符串转换回Interval的方法。我可以从离散化中获取所有Interval值的列表(例如:cuts.unique())并在测试时应用它,但这将需要在随机森林旁边保存/加载离散化字典,这似乎很笨拙,我担心会遇到尝试重新创建分类变量的问题(主要来自R,这对分类变量的格式极为特殊)。还是有另一种我看不到的解决方法?

2 个答案:

答案 0 :(得分:0)

虽然这可能不是看上去最干净的方法,但确实可以将字符串转换回间隔:

import pandas as pd
str_intervals = [i.replace("(","").replace("]", "").split(", ") for i in str_cuts]
original_cuts = [pd.Interval(float(i), float(j)) for i, j in str_intervals]

答案 1 :(得分:0)

使用qcut中的labels参数并使用pandas Categorical

这两种方法都可以帮助您创建类别,而不是为变量创建区间。然后,您可以使用一种编码形式,例如Label EncodingOrdinal Encoding将类别(如果您习惯使用R的因素)转换为Forest能够使用的数值。

然后流程进行:

cutting => categoricals => encoding

您不再需要手动操作。

最后,一些梯度增强树库支持分类变量,尽管它不是灵丹妙药,并且将取决于您的目标。参见catboostlightgbm