【问题标题】:String to array in spark字符串到火花中的数组
【发布时间】:2018-06-13 22:57:06
【问题描述】:

我在 PySpark 中有一个数据框,其中包含一个值为 [{"AppId":"APACON","ExtId":"141730"}] 的字符串列(该字符串与我的列中的字符串完全相同,它是一个字符串,而不是数组)

我想将其转换为结构数组。

我可以简单地使用本机 spark 函数来做到这一点,还是必须解析字符串或使用 UDF?

sqlContext.createDataFrame(
    [ (1,'[{"AppId":"APACON","ExtId":"141730"}]'),
      (2,'[{"AppId":"APACON","ExtId":"141793"}]'),
    ],
    ['idx','txt']
).show()

+---+--------------------+
|idx|                 txt|
+---+--------------------+
|  1|[{"AppId":"APACON...|
|  2|[{"AppId":"APACON...|
+---+--------------------+

【问题讨论】:

  • 你需要from_json
  • 在 2.0 中不可用......还有其他选择吗?
  • 您可以尝试 pyspark.sql.functions.get_json_object 它将解析 txt 列并为每个字段创建一个具有关联值的列
  • @plalanne 解析 json,但我不知道如何访问列表中的元素。
  • 我编辑了我的答案并提出了一个正则表达式来忽略 df.txt 中的方括号作为第一步。让我知道这是否有帮助

标签: python apache-spark pyspark


【解决方案1】:

使用 Spark 2.1 或更高版本

您有以下数据:

import pyspark.sql.functions as F
from pyspark.sql.types import *

df = sqlContext.createDataFrame(
    [ (1,'[{"AppId":"APACON","ExtId":"141730"}]'),
      (2,'[{"AppId":"APACON","ExtId":"141793"}]'),
    ],
    ['idx','txt']
)

你确实可以使用 pyspark.sql.functions.from_json 如下:

schema = StructType([StructField("AppId", StringType()),
                     StructField("ExtId", StringType())])
df = df.withColumn('array',F.from_json(F.col('txt'), schema))
df.show()

+---+--------------------+---------------+
|idx|                 txt|          array|
+---+--------------------+---------------+
|  1|[{"AppId":"APACON...|[APACON,141730]|
|  2|[{"AppId":"APACON...|[APACON,141793]|
+---+--------------------+---------------+


版本

绕过该问题的一种方法是首先稍微修改您的输入字符串:

# Use regexp_extract to ignore square brackets
df.withColumn('txt_parsed',F.regexp_extract(F.col('txt'),'[^\\[\\]]+',0))
df.show()

+---+-------------------------------------+-----------------------------------+
|idx|txt                                  |txt_parsed                         |
+---+-------------------------------------+-----------------------------------+
|1  |[{"AppId":"APACON","ExtId":"141730"}]|{"AppId":"APACON","ExtId":"141730"}|
|2  |[{"AppId":"APACON","ExtId":"141793"}]|{"AppId":"APACON","ExtId":"141793"}|
+---+-------------------------------------+-----------------------------------+

然后你可以使用 pyspark.sql.functions.get_json_object 来解析 txt 列

df = df.withColumn('AppId', F.get_json_object(df.txt, '$.AppId'))
df = df.withColumn('ExtId', F.get_json_object(df.txt, '$.ExtId'))
df.show()


+---+--------------------+------+------+
|idx|                 txt| AppId| ExtId|
+---+--------------------+------+------+
|  1|{"AppId":"APACON"...|APACON|141730|
|  2|{"AppId":"APACON"...|APACON|141793|
+---+--------------------+------+------+

【讨论】:

    猜你喜欢
    • 2019-10-22
    • 1970-01-01
    • 1970-01-01
    • 2018-02-18
    • 2021-07-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-04-22
    相关资源
    最近更新 更多