【问题标题】:Text field concatenation in sklearn pipelinesklearn管道中的文本字段连接
【发布时间】:2018-09-26 09:49:10
【问题描述】:

我有一个多行 json 数据集,其中包含多个可以存在或不存在的字段,并且可以包含字符串、字符串列表或更复杂的映射(dicts 列表)中的文本数据

例如:

{"yvalue":1.0,"field1":"Some text", "field2":"More Text", "field3": ["text","items","in","list"], "field4":[{"id":3,"name":"text"},{"id":4,"name":"text"}]}
{"yvalue":2.0,"field2":"More Text2", "field3": ["text2","items2","in2","list2"], "field4":[{"id":4,"name":"text"},{"id":4,"name":"text"}], "field5":"extra text"}
...

需要此数据集作为 sklearn 管道的输入

首先我通过 pandas 读取文件

df = pandas.read_json(args.input_file, lines=True)

但我想使用像DataframeMapper 这样的管道转换器将所有文本字段(甚至是嵌套的)连接到一个巨大的文本字段。考虑到某些字段可能会丢失,是嵌套结构的一部分等。

输出类似于:

y 值 |文字

1.0 |列表文本文本中的一些文本更多文本文本项

2.0 | More Text2 text2 items2 in2 list2 text text extra text

当然我可以使用自定义转换器,但由于我也有兴趣将管道转换为 mleap 或 pmml 格式,因此我宁愿尽可能避免使用自定义转换器。

有没有最佳实践甚至简单的方法来做到这一点而不会太老套?


更新

显然我想要的可能有点太多了,但也许更简单: 有没有办法使用 Pandas 中的转换器连接 2 个(或更多)类似字符串的字段:

df[['field1', 'field2']].apply(lambda x: ' '.join(x.astype(str)), axis=1)

【问题讨论】:

  • 我认为您不会为此准备好任何东西。您可以做的是将处理部分与管道分开。将json输入转换为二维数组的东西,然后可以传递给管道。 Pmml 会处理管道,你可以用任何你喜欢的语言重新编码转换器部分,我认为没有太多麻烦。
  • json 到二维数组将变得容易,如果您可以将 json 转换为 pojo 类型的对象,然后只使用该对象的字符串表示返回所需的行(包含所有数据,和该json不存在的字段的一些默认值或空值)
  • 感谢 Vivek,您的反应。我认为这将是最实用的方法。但我并不熟悉 sklearn 必须提供的所有可能的转换器。
  • 对不起,我不知道有任何内置转换器可以处理 json 到 2-d 数组的转换,如果那是你想要的。

标签: python scikit-learn sklearn-pandas pmml mleap


【解决方案1】:

考虑重构您的数据预处理。 Scikit-Learn 管道不是进行低级数据清理/准备工作的地方,例如解包集合,以及(有条件地)将文本字段连接到文本文档中。

这是一项常规编程任务,而不是机器学习任务。因此,您应该使用常规编程工具,而不是机器学习工具(例如 Scikit-Learn 转换器)来完成它。 PMML 和 MLeap 都不适合低级文本处理。

【讨论】:

  • 你当然是对的。我只是在寻找一种方法来规避这个
【解决方案2】:

使用管道和转换器来简化模型的可解释性(例如 shap 值)是合理的,而不是直接的 Pandas-only 预处理。

假设一个数据框 X 的文本列:


    class StringConcatTransformer(TransformerMixin, BaseEstimator):
        """Concatenate multiple string fields into a single field.
        """
        
        def __init__(self, missing_indicator=''):
            self.missing_indicator = missing_indicator

        def fit(self, X, y=None, **fit_params):
            return self

        def transform(self, X, y=None):
            return X.fillna(self.missing_indicator).agg(' '.join, axis=1)

【讨论】:

    猜你喜欢
    • 2019-10-05
    • 2014-10-21
    • 1970-01-01
    • 2016-07-06
    • 2015-08-27
    • 1970-01-01
    • 1970-01-01
    • 2014-01-29
    相关资源
    最近更新 更多