首页 > 解决方案 > 连接结构数组的方法

问题描述

我有一列包含结构数组。它看起来像这样:

 |-- Network: array (nullable = true)
 |    |-- element: struct (containsNull = true)
 |    |    |-- Code: string (nullable = true)
 |    |    |-- Signal: string (nullable = true)

这只是一个小样本,结构内的列比这多得多。有没有办法为每一行获取列中的数组,将它们连接起来并将它们变成一个字符串?例如,我们可以有这样的东西:

[["example", 2], ["example2", 3]]

有没有办法做成:

"example2example3"?

标签: apache-spark

解决方案


假设有一个df具有以下模式的数据框:

df.printSchema

在此处输入图像描述

df带有样本数据:

df.show(false)

在此处输入图像描述

您需要首先分解网络数组以选择结构元素代码和信号。

var myDf = df.select(explode($"Network").as("Network"))

然后,您需要使用 concat() 函数连接两列,然后将输出传递给 collect_list() 函数,该函数会将所有行聚合为 array<string> 类型的一行

myDf = myDf.select(collect_list(concat($"Network.code",$"Network.signal")).as("data"))

最后,您需要连接成所需的格式,这可以使用 concat_ws() 函数完成,该函数接受两个参数,第一个是放置在两个字符串之间的分隔符,第二个参数是 array<string> 类型的列我们上一步的输出。根据您的用例,我们不需要在两个连接字符串之间放置任何分隔符,因此我们将分隔符参数保留为空引号。

myDf = myDf.select(concat_ws("",$"data").as("data"))

以上所有步骤都可以在一行中完成

myDf= myDf.select(explode($"Network").as("Network")).select(concat_ws("",collect_list(concat($"Network.code",$"Network.signal"))).as("data")).show(false)

在此处输入图像描述

如果您希望将输出直接转换为 String 变量,请使用:

val myStr = myDf.first.get(0).toString
print(myStr)

ex11ex22ex331


推荐阅读