Spark SQL:如何将特定函数应用于所有指定的列

时间:2017-05-18 17:22:11

标签: sql apache-spark apache-spark-sql

我有一种简单的方法可以在spark sql上的多个列上调用sql。

例如,假设我有一个应该应用于大多数列的查询

select
min(c1) as min,
max(c1) as max,
max(c1) - min(c1) range
from table tb1

如果有多列,是否有办法对所有列执行查询,并获得一次结果。

df.describe 的方式类似。

1 个答案:

答案 0 :(得分:1)

使用数据框中包含的元数据(本例中的列)(如果您还没有在范围内获取列名,可以通过spark.table("<table_name>")获取),然后应用这些功能你想要并传递给df.select(或df.selectExpr)。

构建一些测试数据:

scala> var seq = Seq[(Int, Int, Float)]()
seq: Seq[(Int, Int, Float)] = List()

scala> (1 to 1000).foreach(n => { seq = seq :+ (n,r.nextInt,r.nextFloat) })

scala> val df = seq.toDF("id", "some_int", "some_float")

表示我们想要在所有列上运行的一些函数:

scala> val functions_to_apply = Seq("min", "max")
functions_to_apply: Seq[String] = List(min, max)

设置SQL列的最终Seq:

scala> var select_columns = Seq[org.apache.spark.sql.Column]()
select_columns: Seq[org.apache.spark.sql.Column] = List()

迭代要应用的列和函数来填充select_columns Seq:

scala> val cols = df.columns

scala> cols.foreach(col => { functions_to_apply.foreach(f => {select_columns = select_columns :+ expr(s"$f($col)")})})

运行实际查询:

scala> df.select(select_columns:_*).show

+-------+-------+-------------+-------------+---------------+---------------+
|min(id)|max(id)|min(some_int)|max(some_int)|min(some_float)|max(some_float)|
+-------+-------+-------------+-------------+---------------+---------------+
|      1|   1000|  -2143898568|   2147289642|   1.8781424E-4|     0.99964607|
+-------+-------+-------------+-------------+---------------+---------------+