Apache spark 如何使用DataFrame处理数据并插入新列

Apache spark 如何使用DataFrame处理数据并插入新列,apache-spark,apache-spark-sql,spark-dataframe,Apache Spark,Apache Spark Sql,Spark Dataframe,后代码 val df = spark.sql(sql_query) df.show() 我得到了一个模式 // +--------+-------+ // | id_card| year| // +--------+-------+ // |001_1976| 2017 | // |015_1983| 2012 | // |078_1963| 2011 | // +--------+-------+ 然后我想得到一个名为“工作年”的新列(年-id\u-card.substring(

后代码

val df = spark.sql(sql_query)
df.show()
我得到了一个模式

// +--------+-------+
// | id_card|   year|
// +--------+-------+
// |001_1976| 2017  |
// |015_1983| 2012  |
// |078_1963| 2011  |
// +--------+-------+
然后我想得到一个名为“工作年”的新列
(年-id\u-card.substring(4,8))
我已经阅读了关于
withColumn()
的源代码,我注意到
withColumn
的列参数必须是
org.apache.spark.sqlColumn
,而不是简单的字符串,这确实让我不安

spark version: Spark 2.1.0 

scala version: 2.12.1

jdk version: 1.8

您可以使用数据帧df上的
withColumn
函数以及udf来完成此操作

import org.apache.spark.sql.functions.udf

val df = sc.parallelize((Seq(("001_1976", 2017),("015_1983", 2012),("078_1963", 2011)))).toDF("c1", "c2")

val work_year = udf((x: String) => x.substring(4,8))

scala> df.withColumn("work_year", work_year($"c1")).show()
+--------+----+---------+
|      c1|  c2|work_year|
+--------+----+---------+
|001_1976|2017|     1976|
|015_1983|2012|     1983|
|078_1963|2011|     1963|
+--------+----+---------+
或者使用spark sql,如下所示

df.registerTempTable("temp_table")

scala> spark.sql("SELECT c1,c2, substring(c1,5,8) from temp_table").show()
+--------+----+-------------------+
|      c1|  c2|substring(c1, 5, 8)|
+--------+----+-------------------+
|001_1976|2017|               1976|
|015_1983|2012|               1983|
|078_1963|2011|               1963|
+--------+----+-------------------+

您可以使用数据帧df上的
withColumn
函数以及udf来完成此操作

import org.apache.spark.sql.functions.udf

val df = sc.parallelize((Seq(("001_1976", 2017),("015_1983", 2012),("078_1963", 2011)))).toDF("c1", "c2")

val work_year = udf((x: String) => x.substring(4,8))

scala> df.withColumn("work_year", work_year($"c1")).show()
+--------+----+---------+
|      c1|  c2|work_year|
+--------+----+---------+
|001_1976|2017|     1976|
|015_1983|2012|     1983|
|078_1963|2011|     1963|
+--------+----+---------+
或者使用spark sql,如下所示

df.registerTempTable("temp_table")

scala> spark.sql("SELECT c1,c2, substring(c1,5,8) from temp_table").show()
+--------+----+-------------------+
|      c1|  c2|substring(c1, 5, 8)|
+--------+----+-------------------+
|001_1976|2017|               1976|
|015_1983|2012|               1983|
|078_1963|2011|               1963|
+--------+----+-------------------+

扩展到@rogue one-answer

正如OP询问的
work\u year=(year-id\u card.substring(4,8))

那么udf应该是

val work_year = udf((x: String, y: Int) => y - x.substring(4,8).toInt)

df.withColumn("work_year", work_year($"id_card", $"year")).show()
输出:

+--------+----+---------+
| id_card|year|work_year|
+--------+----+---------+
|001_1976|2017|       41|
|015_1983|2012|       29|
|078_1963|2011|       48|
+--------+----+---------+

扩展到@rogue one-answer

正如OP询问的
work\u year=(year-id\u card.substring(4,8))

那么udf应该是

val work_year = udf((x: String, y: Int) => y - x.substring(4,8).toInt)

df.withColumn("work_year", work_year($"id_card", $"year")).show()
输出:

+--------+----+---------+
| id_card|year|work_year|
+--------+----+---------+
|001_1976|2017|       41|
|015_1983|2012|       29|
|078_1963|2011|       48|
+--------+----+---------+

请问JAVA版本如何?JAVA版本应该是无关的。但我会推荐至少Java7+谢谢,它在scala中工作!我不能在java中使用“$”,如何将这些代码翻译成java?那会是什么?请问JAVA版本呢?JAVA版本应该是不相关的。但我会推荐至少Java7+谢谢,它在scala中工作!我不能在java中使用“$”,如何将这些代码翻译成java?会是什么?