scala - Spark/scala - 我们可以从数据框中的现有列值创建新列吗
问题描述
我想看看我们是否可以使用 spark/scala 从 dataFrame 中的一列中的值创建新列。我有一个包含以下数据的数据框
df.show()
+---+-----------------------+
|id |allvals |
+---+-----------------------+
|1 |col1,val11|col3,val31 |
|3 |col3,val33|col1,val13 |
|2 |col2,val22 |
+---+-----------------------+
在上面的数据中 col1/col2/col3 是列名后跟它的值。列名和值用 分隔,
。每组由 分隔|
。
现在,我想实现这样
+---+----------------------+------+------+------+
|id |allvals |col1 |col2 |col3 |
+---+----------------------+------+------+------+
|1 |col1,val11|col3,val31 |val11 |null |val31 |
|3 |col3,val33|col1,val13 |val13 |null |val13 |
|2 |col2,val22 |null |val22 |null |
+---+----------------------+------+------+------+
感谢任何帮助。
解决方案
split
您可以使用,explode
和转换 DataFrame groupBy/pivot/agg
,如下所示:
val df = Seq(
(1, "col1,val11|col3,val31"),
(2, "col3,val33|col1,val13"),
(3, "col2,val22")
).toDF("id", "allvals")
import org.apache.spark.sql.functions._
df.withColumn("temp", split($"allvals", "\\|")).
withColumn("temp", explode($"temp")).
withColumn("temp", split($"temp", ",")).
select($"id", $"allvals", $"temp".getItem(0).as("k"), $"temp".getItem(1).as("v")).
groupBy($"id", $"allvals").pivot("k").agg(first($"v"))
// +---+---------------------+-----+-----+-----+
// |id |allvals |col1 |col2 |col3 |
// +---+---------------------+-----+-----+-----+
// |1 |col1,val11|col3,val31|val11|null |val31|
// |3 |col2,val22 |null |val22|null |
// |2 |col3,val33|col1,val13|val13|null |val33|
// +---+---------------------+-----+-----+-----+
推荐阅读
- xml - 使用 BaseX POST 方法在 xquery 中传递 <>
- javascript - 如果我的 LDAP 服务器上不存在用户名,则无限加载我的 NodeJS API 站点
- vue.js - 什么是用于处理在 vue.js 中还包含可选字符和货币过滤器的掩码的插件?
- javascript - React 组件中的样式属性不止一种样式
- sharepoint - 如何在共享点网站的项目详细信息页面中嵌入 Power bi 报告?(无需 Office 365 租户即可完成本地设置)
- java - 如何使用 xstream 将地图中根元素的名称更改为 xml 转换
- powershell - 是否有一种方法可以翻转子网掩码中的位以使用 PowerShell 获取通配符掩码?
- python - 当间隔的位置由索引列表定义时,如何在 pandas 数据框中的行间隔上切片和应用函数?
- typescript - 在 Typescript 界面上强制执行单个必需属性,允许其他属性
- python - 处理闰日,无论是存在还是不存在