Spark操作—aggregate

1、aggregate

首先看下 aggregate 函数签名

 def aggregate[U: ClassTag](zeroValue: U)(seqOp: (U, T) => U, combOp: (U, U) => U): U

说明

参数zeroValue:seqOp运算符的每个分区的累积结果的初始值以及combOp运算符的不同分区的组合结果的初始值 - 这通常将是初始元素(例如“Nil”表的列表 连接或“0”表示求和) 
参数seqOp: 每个分区累积结果的聚集函数。 
参数combOp: 一个关联运算符用于组合不同分区的结

应用举例

数据准备

  //获取 SparkConf 并设置应用名称*本地模式
    val conf: SparkConf = new SparkConf().setAppName("Spark").setMaster("local[*]")
    //获取 Spark 上下文对象
    val sc: SparkContext = new SparkContext(conf)
    val rdd:RDD[Int] = sc.makeRDD(List(1, 2, 3, 4), 2)
    rdd.mapPartitionsWithIndex {
      case (index, data) => {
        println(index + " -> " + data.mkString(","))
      }
        data
    }.collect().foreach(println)

输出

1 -> 3,4
0 -> 1,2

需求1:默认值 0 ,分区内求和,分区间求和

 println(rdd.aggregate(0)(_ + _, _ + _))

分析

    /**
     * 0 -> 0 + 1 + 2 => 3
     * 1 -> 0 + 3 + 4 => 7
     * 0 -> 3
     * 1 -> 7
     * 0 + 3 + 7
     * 10 + 0
     * 10
     */

需求2:默认值 10 ,分区内求和,分区间求和

    /**
     * 0 -> 10 + 1 + 2 => 13
     * 1 -> 10 + 3 + 4 => 17
     * 0 -> 13
     * 1 -> 17
     * 10 + 13  + 17  
     * 40
     */

需求3:分区内求最大值,分区间求和

 println(rdd.aggregate(2)(math.max(_, _), _ + _))

分析

    /**
     * 0 -> max(2,1,2) => 2
     * 1 -> max(2,3,4) => 4
     * 0 -> 2
     * 1 -> 4
     * 2 + 2 + 4
     * 8
     */

接下来看下 书本上的一个案例

    val tuple: (Int, Int) = rdd.aggregate((0, 0))(
      (acc, value) => (acc._1 + value, acc._2 + 1),
      (acc1, acc2) => (acc1._1 + acc2._1, acc1._2 + acc2._2)
    )
    println(tuple)
    println(tuple._1 / tuple._2.toDouble)
posted @ 2022-06-17 10:09  晓枫的春天  阅读(145)  评论(0编辑  收藏  举报