Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/apache-kafka/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何在pyspark中连接不同的映射类型_Pyspark_Apache Spark Sql - Fatal编程技术网

如何在pyspark中连接不同的映射类型

如何在pyspark中连接不同的映射类型,pyspark,apache-spark-sql,Pyspark,Apache Spark Sql,我有不同的地图类型,如下所示: MapType(StringType(), StringType()) MapType(StringType(), IntegerType()) MapType(StringType(), DoubleType()) 如何将其合并为一个并保持其类型完整?您可以合并具有不同键和值类型的maptype列。但是post concat spark将映射键/值类型转换为它找到的最高类型 比如说- 如果考虑3列具有以下类型的RESP.-/P> col1-MapType(St

我有不同的地图类型,如下所示:

MapType(StringType(), StringType())
MapType(StringType(), IntegerType())
MapType(StringType(), DoubleType())

如何将其合并为一个并保持其类型完整?

您可以合并具有不同键和值类型的
maptype
列。但是post concat spark将映射键/值类型转换为它找到的最高类型

比如说- 如果考虑3列具有以下类型的RESP.-/P>
col1-MapType(StringType(),StringType())
col2-映射类型(StringType(),IntegerType())
col3-映射类型(StringType(),DoubleType())
map\u concat
输出如下-

map_concat(col1, col2, col3) - MapType(StringType(), StringType())
因为spark发现键和值的最高类型为
StringType

现在,

为什么spark不能保持键值对的原始类型不变

Ans- Spark将MapType存储为由2个ArrayData支持的

类ArrayBasedMapData(val-keyArray:ArrayData,val-valueArray:ArrayData)扩展了MapData{
...
}
&ArrayData无法处理异构类型。因此,spark不能在连接后保持其原始类型不变

工作示例供参考
val df=spark.sql(“选择map('a','b')作为col1,选择map('c',cast(1作为int))作为col2,”+
“地图(1,铸造(2.2倍))为col3”)
df.printSchema()
df.show(假)
/**
*根
*|--col1:map(nullable=false)
*| |--键:字符串
*| |--value:string(valuecontainsnall=false)
*|--col2:map(nullable=false)
*| |--键:字符串
*| |--值:整数(valuecontainsnall=false)
*|--col3:map(nullable=false)
*| |--键:字符串
*| |--value:double(valuecontainsnall=false)
*
* +--------+--------+----------+
*| col1 | col2 | col3|
* +--------+--------+----------+
*|[a->b]|[c->1]|[d->2.2]|
* +--------+--------+----------+
*/
val p=df.withColumn(“新列”,映射列($“col1”,“$“col2”,“$“col3”))
p、 printSchema()
p、 显示(假)
/**
*根
*|--col1:map(nullable=false)
*| |--键:字符串
*| |--value:string(valuecontainsnall=false)
*|--col2:map(nullable=false)
*| |--键:字符串
*| |--值:整数(valuecontainsnall=false)
*|--col3:map(nullable=false)
*| |--键:字符串
*| |--value:double(valuecontainsnall=false)
*|--new_col:map(nullable=false)
*| |--键:字符串
*| |--value:string(valuecontainsnall=false)
*
* +--------+--------+----------+--------------------------+
*| col1 | col2 | col3 | new|u col|
* +--------+--------+----------+--------------------------+
*|[a->b]|[c->1]|[d->2.2]|[a->b,c->1,d->2.2]|
* +--------+--------+----------+--------------------------+
*/
更新-1
使用struct将列合并为一个

val x=df.withColumn(“x”,结构($“col1”,“$”col2”,“$”col3”))
x、 printSchema()
x、 selectExpr(“x.col1['a'],“x.col2['c'],“x.col3['d']”)。printSchema()
/**
*根
*|--col1:map(nullable=false)
*| |--键:字符串
*| |--value:string(valuecontainsnall=false)
*|--col2:map(nullable=false)
*| |--键:字符串
*| |--值:整数(valuecontainsnall=false)
*|--col3:map(nullable=false)
*| |--键:整数
*| |--value:double(valuecontainsnall=false)
*|--x:struct(nullable=false)
*| |--col1:map(nullable=false)
*| | |--键:字符串
*| | |--value:string(valuecontainsnall=false)
*| |--col2:map(nullable=false)
*| | |--键:字符串
*| | |--值:整数(valuecontainsnall=false)
*| |--col3:map(nullable=false)
*| | |--键:整数
*| | |--value:double(valuecontainsnall=false)
*
*根
*|--x.col1作为'col1`[a]:字符串(nullable=true)
*|--x.col2作为'col2`[c]:整数(nullable=true)
*|--x.col3 AS`col3`[强制转换(d AS INT)]:double(nullable=true)
*/

谢谢你的回复。我只是这样做了,但它保留了地图(字符串,字符串)然而,我希望类型与第1,2,3列中的类型保持一致。因为它将流式处理kafka,其中模式与第1,2,3列相同。但是第3列正在改变这一点。是否有其他方法可以使用struct或其他方法?可以使用struct将所有3个maptype列合并到一个列中。检查更新-1。如果有帮助的话,也可以随意投票并接受