我对Apache Spark很新,并且有时仍在努力解决它。我试图导入一个非常复杂的json文件并将其压平,然后将其保存在镶木地板文件中。
我的json文件是商店树。
{
"id": "store02",
"name": "store name",
"domain": "domain",
"currency": "EUR",
"address1": "Somewhere",
"country": "GER",
"city": "Berlin",
"zipCode": "12345",
"timeZone": "CET",
"accounts" : [
{
"field1": "",
"filed2": "",
"field3": "",
"optionnalArray1": [
{
"field1": "",
"field2": ""
}
],
"optionnalArray2": ["aa", "bb"]
}
],
"stores": [ .... ]
}
每个商店都有一个字段,其中包含一系列帐户。一个帐户有3个必填字段和两个选项。所以我有一个数据框,其中包含一个可以有3种不同类型的字段。
在数据框中导入文件没什么大不了的,但在展平过程中我可能想要在两个数据框架上进行联合,这些数据框架的帐户可能有不同的模式,当然我有以下错误:" Union只能在具有兼容列类型"
的表上执行有没有办法轻松地做到这一点?如何引发这样的json文件没有问题呢?
@Ramesh
我们说我有两个数据帧。第一个是没有帐户的商店的数据框。第二个是具有帐户的商店的数据框。帐户是这样定义的结构:
val acquirerStruct = StructType(
StructField("merchantId", StringType, nullable = true) ::
StructField("name", StringType, nullable = true) ::
Nil)
val accountStruct = StructType(
StructField("acquirers", ArrayType(acquirerStruct), nullable = true) ::
StructField("applicationCode", StringType, nullable = true) ::
StructField("channelType", StringType, nullable = true) ::
StructField("id", StringType, nullable = true) ::
StructField("terminals", ArrayType(StringType), nullable = true) ::
Nil)
当我想要联合两个数据帧时,我会在第一个数据帧之前创建一个列帐户:
df1.withColumn("account", array(lit(null).cast(accountStruct))).union(df2)
如果在df2中,所有行的帐户都具有与accountStruct相同的结构,那么它可以正常工作。但这并非总是如此。帐户可能没有终端或收单方。这在json中完全有效。在那种情况下,我之前提到了错误。
"Union can only be performed on tables with the compatible column types"
答案 0 :(得分:0)
我在PySpark中遇到了同样的问题,我在读取不兼容的数据帧时通过提供模式来解决了这个问题
import copy
...
schema_to_read = copy.deepcopy(df1.schema)
df2 = sql_context.read.format("json").schema(schema_to_read).load(path)