Spark Scala中嵌套模式的字符串函数

Spark Scala中嵌套模式的字符串函数,scala,apache-spark,Scala,Apache Spark,我正在用Scala编程语言学习Spark 输入文件-> “个人”:{“ID”:3424,“姓名”:[“abcs”,“dakjdb”]} 架构-> root |-- Personal: struct (nullable = true) | |-- ID: integer (nullable = true) | |-- Name: array (nullable = true) | | |-- element: string (containsNull = t

我正在用Scala编程语言学习Spark

输入文件-> “个人”:{“ID”:3424,“姓名”:[“abcs”,“dakjdb”]}

架构->

root
  |-- Personal: struct (nullable = true)
  |    |-- ID: integer (nullable = true)
  |    |-- Name: array (nullable = true)
  |    |    |-- element: string (containsNull = true)
输出操作-> 我想对“Name”元素的字符串进行压缩 Eg-abcs | dakjdb

我正在使用DataFrameAPI读取文件。
请帮助我。

这里有一个内置函数应该很有用。

这里有一个内置函数应该很有用。

如果您使用Spark>=1.6.0,它应该非常简单,您可以使用
获取json\u对象
concat\ws

import org.apache.spark.sql.functions.{get_json_object,concat_ws}
val df=Seq(
(“{”个人“:{”ID“:3424,“姓名“:[“abcs”,“dakjdb”]}}}”),
(“{”个人“:{”ID“:3425,“姓名“:[“cfg”,“woooww”]}}}”)
)
.toDF(“数据”)
选择(
海螺(
"-", 
get_json_对象($“数据”,“$.Personal.Name[0]”),
获取json对象($“数据”,“$.Personal.Name[1]”)
).as(“全名”)
).show(假)
// +-----------+
//|全名|
// +-----------+
//| abcs dakjdb|
//| cfg woooww|
// +-----------+

使用
get_json\u object
我们遍历json数据,提取
Name
数组中的两个元素,稍后将它们连接起来

如果您使用Spark>=1.6.0,那么应该非常简单,您可以使用
get\u json\u object
concat\u ws

import org.apache.spark.sql.functions.{get_json_object,concat_ws}
val df=Seq(
(“{”个人“:{”ID“:3424,“姓名“:[“abcs”,“dakjdb”]}}}”),
(“{”个人“:{”ID“:3425,“姓名“:[“cfg”,“woooww”]}}}”)
)
.toDF(“数据”)
选择(
海螺(
"-", 
get_json_对象($“数据”,“$.Personal.Name[0]”),
获取json对象($“数据”,“$.Personal.Name[1]”)
).as(“全名”)
).show(假)
// +-----------+
//|全名|
// +-----------+
//| abcs dakjdb|
//| cfg woooww|
// +-----------+

使用
get_json\u object
我们遍历json数据,提取
Name
数组中的两个元素,稍后将它们连接起来

扩展@Alexandros Biratsis答案。在连接之前,可以先将名称转换为array[String]类型,以避免写入每个名称位置。当值为null或仅存在一个值而不是两个值时,按位置查询也将失败

import org.apache.spark.sql.functions.{get_json_object, concat_ws, from_json}
import org.apache.spark.sql.types.{ArrayType, StringType}

val arraySchema = ArrayType(StringType)

val df = Seq(
  ("""{"Personal":{"ID":3424,"Name":["abcs","dakjdb"]}}"""),
  ("""{"Personal":{"ID":3425,"Name":["cfg","woooww"]}}""")
)
.toDF("data")
.select(get_json_object($"data", "$.Personal.Name") as "name")
.select(from_json($"name", arraySchema) as "name")
.select(concat_ws("|", $"name"))
.show(false)

扩展@Alexandros Biratsis答案。在连接之前,可以先将名称转换为array[String]类型,以避免写入每个名称位置。当值为null或仅存在一个值而不是两个值时,按位置查询也将失败

import org.apache.spark.sql.functions.{get_json_object, concat_ws, from_json}
import org.apache.spark.sql.types.{ArrayType, StringType}

val arraySchema = ArrayType(StringType)

val df = Seq(
  ("""{"Personal":{"ID":3424,"Name":["abcs","dakjdb"]}}"""),
  ("""{"Personal":{"ID":3425,"Name":["cfg","woooww"]}}""")
)
.toDF("data")
.select(get_json_object($"data", "$.Personal.Name") as "name")
.select(from_json($"name", arraySchema) as "name")
.select(concat_ws("|", $"name"))
.show(false)

你能通过一些示例代码给我一些想法吗?我尝试了下面的代码,但得到了ExpressionEncoder错误\n val value=readFile.select(“Personal”).map(r=>{val array=r.isInstanceOf[mutable.wrappedaraybuilder]array.toString.concat(“|”)(行编码器(schema1))你能通过一些示例代码给我一些想法吗?我尝试了下面的代码,但得到了ExpressionEncoder错误\n val value=readFile.select(“Personal”).map(r=>{val array=r.isInstanceOf[mutable.wrappedarray builder]array.toString.concat(“|”)(RowEncoder(schema1))谢谢你的回答。但当我将模式设置为StructType(List(StructField(“Personal”)、StructType(List(StructField(“ID”、IntegerType,true)、StructField(“Name”、ArrayType(StringType,true‘‘)’))时,它失败了。get_json_对象没有得到任何模式,它将解析json并根据指定的选择器提取所需的数据,即:“$.Personal.Name[0]”。如果您需要验证您的模式,尽管您必须使用from json。这将json存储为一个结构。最后,您可以使用Spark选择器提取数据谢谢您的回答。但当我将模式设置为StructType(List(StructField(“Personal”)、StructType(List(StructField(“ID”、IntegerType,true)、StructField(“Name”、ArrayType(StringType,true‘‘)’))时,它失败了。get_json_对象没有得到任何模式,它将解析json并根据指定的选择器提取所需的数据,即:“$.Personal.Name[0]”。如果您需要验证您的模式,尽管您必须使用from json。这将json存储为一个结构。最后,您可以使用Spark选择器提取数据