单个功能执行多项操作

时间:2019-09-11 17:14:04

标签: dataframe apache-spark

我有一个数据框,我需要对其进行汇总。我是这样的。

ioctl()

看起来还不错,但是如果df .groupBy($"key1", $"key2") .agg( sum($"total_in").as("total_in") , sum($"val1_in").as("val1_in") , sum($"val2_in").as("val2_in") , sum($"val3_in").as("val3_in") , sum($"val4_in").as("val4_in") , sum($"total_out").as("total_out") , sum($"val1_out").as("val1_out") , sum($"val2_out").as("val2_out") , sum($"val3_out").as("val3_out") , sum($"val4_out").as("val4_out")) 中的操作数变大,或者每个agg中添加了case when或其他逻辑,则此代码将看起来真的很麻烦。

我知道可以做到。也许将列传递给一个函数并对其进行迭代。像

sum

但这是我遇到的问题。如何仅传递所需的列?可以在同一位置为它们加上别名吗?

2 个答案:

答案 0 :(得分:0)

使用 vararg 语法:

在python中:

cols = ['total_in', 'val1_in', 'val2_in', ...]
.agg(*(sum(col).alias(col) for col in cols))

在Scala中:

cols = Seq("total_in", "val1_in", "val2_in", ...)
.agg(
  sum(col(cols.head)).as(cols.head), 
  cols.tail.map(x => sum(col(x)).as(x)): _*
)

答案 1 :(得分:0)

我会这样:

val aggExpresion =
    df.columns
      .filterNot(Seq("key1","key2").contains(_))
      .map(s => sum(col(s)).as(s))

df.agg(aggExpresion.head,aggExpresion.tail:_*)