从这里学习的,讲的真好~ https://www.bilibili.com/video/av62992342/?p=41
单数据
MAP
1.作用
返回一个新RDD,该RDD由每个输入元素经过func函数转换后组成。
2.需求
创建一个1-10数组的RDD,将所有元素*2形成新的RDD
3.解
val conf = new SparkConf().setMaster("local[*]").setAppName("mapTest")
val sc = new SparkContext(conf)
val inclusive = 1 to 10
// 算子
val listRDD :RDD[Int] = sc.makeRDD(inclusive)
// 做了映射转换后的RDD
val mapRDD = listRDD.map( _ * 2 )
//
mapRDD.collect().foreach(println)
mapPartitions(func)案例
1.作用
类似于map,但是独立在RDD的每个分片(区)上运行,因此在类型为T的RDD上运行时,func的函数类型必须是Iterator[T]=>Iterator[U]。假设有N个元素,有M个分区,那么map函数将被调用N次,mapPartitions函数被调用M次,一个函数一次处理所有分区。
2.需求
创建一个RDD,使每个元素*2 组成新RDD
3.解
val conf = new SparkConf().setMaster("local[*]").setAppName("mapPartitionsTest")
val sc = new SparkContext(conf)
val inclusive = 1 to 10
// 算子
val listRDD: RDD[Int] = sc.makeRDD(inclusive)
// 做了映射转换后的RDD
// mapPartitions可以对一个RDD中所有分区进行遍历
val mapPartitions = listRDD.mapPartitions(datas => {
datas.map(data => data * 2)
})
mapPartitions.collect().foreach(println)
mapPartitions效率优于map算子,减少了发送到执行器执行交互的次数。
但是要注意!发送的是整个分区数据,可能会比较大。。。这里回收机制和GC里可达性分析类似,所以处理完的分区不会立即释放,内存占用高,可能会出现内存溢出OOM。
mapPartitionsWithIndex(func)案例
1.作用
类似mapPartitions,但是func带一个整数参数,表示分片的索引值。因此在类型为T的RDD上运行,func的函数类型必须是(Int,Interator[T])=>Iterator[U];
2.需求
创建一个RDD,使每个元素跟所在分区形成一个元组组成一个新的RDD
3.解
val conf = new SparkConf().setMaster("local[*]").setAppName("mapPartitionsWithIndex")
val sc = new SparkContext(conf)
val listRDD = sc.makeRDD(1 to 10,2)
val indexRdd = listRDD.mapPartitionsWithIndex {
case (num, datas) => {
datas.map((_, "分区号:" + num))
}
}
indexRdd.collect().foreach(println)
FlatMap(func)案例
1.作用
类似于map,但是每个输入元素可以被映射为0或多个输出元素(所以func应该返回一个序列,而非单一元素)
2.需求
创建一个元素1-5的RDD,运用FlatMap创建一个新RDD,新RDD为原RDD每个元素2倍
3.解
val conf = new SparkConf().setMaster("local[*]").setAppName("mapPartitionsWithIndex")
val sc = new SparkContext(conf)
val listRDD = sc.makeRDD(Array(List(1,2),List(3,4)))
// flatMap
// 1,2,3,4
val flatMapRDD = listRDD.flatMap(datas=>datas)
val value = flatMapRDD.map(_*2)
value.collect().foreach(println)
glom
1.作用
将每一个分区形成一个数组,组成新的RDD类型时RDD[Array[T]]
2.例子
val conf = new SparkConf().setMaster("local[*]").setAppName("glom")
val sc = new SparkContext(conf)
val listRDD: RDD[Int] = sc.makeRDD(List(1,2,3,4,5,6,7,8),3)
// 将我们一个分区的数据放到一个数组中
val glomRDD: RDD[Array[Int]] = listRDD.glom()
glomRDD.collect().foreach(array=>{
println(array.mkString(","))
})
groupBy
1.作用
分组,按照传入函数的返回值进行分组。将相同的key 对应值放入一个迭代器中。
2.例子
val conf = new SparkConf().setMaster("local[*]").setAppName("glom")
val sc = new SparkContext(conf)
val listRDD: RDD[Int] = sc.makeRDD(List(1,2,3,4))
// 生成数据 按照指定规则进行分组
// 分组后的数据形成了对偶元组(k-V),k表示分组的key,value表示分组数据集合
val groupByRDD: RDD[(Int, Iterable[Int])] = listRDD.groupBy(i=>i%2)
groupByRDD.collect().foreach(println)
</