Spark——transformation

本文深入探讨了Spark中的transformation操作,包括map、filter、flatMap、groupByKey、reduceByKey、sortByKey以及join和cogroup。这些操作都是延迟执行的,直到遇到action操作时才触发实际计算。通过实例展示了如何使用这些转换来处理RDD,为Spark编程提供关键理解。
摘要由CSDN通过智能技术生成

操作RDD(transformation和action案例实战)

1、transformation和action介绍

  • Spark支持两种RDD操作:transformation和action。
    transformation操作会针对已有的RDD创建一个新的RDD;而action则主要是对RDD进行最后的操作,比如遍历、reduce、保存到文件等,并可以返回结果给Driver程序。

  • 例如,map就是一种transformation操作,它用于将已有RDD的每个元素传入一个自定义的函数,并获取一个新的元素,然后将所有的新元素组成一个新的RDD。
    而reduce就是一种action操作,它用于对RDD中的所有元素进行聚合操作,并获取一个最终的结果,然后返回给Driver程序。

  • transformation的特点就是lazy特性。lazy特性指的是,如果一个spark应用中只定义了transformation操作,那么即使你执行该应用,这些操作也不会执行。
    也就是说,transformation是不会触发spark程序的执行的,它们只是记录了对RDD所做的操作,但是不会自发的执行。只有当transformation之后,接着执行了一个action操作,那么所有的transformation才会执行。
    Spark通过这种lazy特性,来进行底层的spark应用执行的优化,避免产生过多中间结果。

  • action操作执行,会触发一个spark job的运行,从而触发这个action之前所有的transformation的执行。这是action的特性。

2、 transformation

1、算子

map 将RDD中的每个元素传入自定义函数,获取一个新的元素,然后用新的元素组成新的RDD
filter 对RDD中每个元素进行判断,如果返回true则保留,返回false则剔除
flatMap 与map类似,但是对每个元素都可以返回一个或多个新元素
groupByKey 根据key进行分组,每个key对应一个Iterable
reduceByKey 对每个key对应的value进行reduce操作
sortByKey 对key进行排序操作
join 对两个包含<key,value>对的RDD进行join操作,每个key join上的pair,都会传入自定义函数进行处理
cogroup 同join,但是是每个key对应的Iterable都会传入自定义函数进行处理

2)例子
① map

案例1:对每一个元素*2(java)

package cn.spark.study.core;

import org.apache.spark.SparkConf;
import org.apache.spark.api.java.JavaRDD;
import org.apache.spark.api.java.JavaSparkContext;
import org.apache.spark.api.java.function.Function;
import org.apache.spark.api.java.function.VoidFunction;
import java.util.Arrays;
import java.util.List;

public class Transfromation_7 {
   
    public static void main(String[] args) {
   
        myMap();
    }

    private static void myMap(){
   
        SparkConf conf = new SparkConf()
                .setAppName("map")
                .setMaster("local");
        JavaSparkContext sc = new JavaSparkContext(conf);

        //构建集合
        List<Integer> numbers = Arrays.asList(1,2,3,4,5);
        //并行化集合,初始RDD
        JavaRDD<Integer> numberRDD = sc.parallelize(numbers);
        //使用map算子,将集合中的每个元素*2
        // map算子,是对任何算数据类型的RDD都可以调用的
        // 在java中,map算子接收的参数是Function对象
        // 创建的Function对象,一定会让你设置第二个参数,这个泛型参数,就是返回新元素的类型
        // 同时call()方法的返回类型,也必须与第二个个泛型类型同步
        // 在call()可以对原始数据进行各种操作,并返回一组新的元素组成一个新的RDD
        JavaRDD<Integer> map = numberRDD.map(new Function<Integer, Integer>() {
   
            @Override
            public Integer call(Integer integer) throws Exception {
   
                return integer * 2;
            }
        });
        //打印新的RDD中的内容
        map.foreach(new VoidFunction<Integer>() {
   
            @Override
            public void call(Integer integer) throws Exception {
   
                System.out.println(integer);
            }
        });
        sc.close();
    }
}

在这里插入图片描述
案例2:对奇数*2(scala)

package cn.spark.study.core

import org.apache.spark.rdd.RDD
import org.apache.spark.{
   SparkConf, SparkContext}

object Transformation {
   
  def main(args: Array[String]): Unit = {
   
    myMap()
  }
  def myMap (): Unit ={
   
    val conf: SparkConf = new SparkConf()
      .setMaster("local")
      .setAppName("myMap")
  
    val sc: SparkContext = new SparkContext(conf)
  
    val arr = Array(1,2,3,4,5)
    val rddInt: RDD[Int] = sc.parallelize(arr)
    val cheng2Rdd: RDD[Int] = rddInt.map((x: Int) => if (x % 2 != 0) x * 2; else x)
    cheng2Rdd.foreach(println)
  }
}

在这里插入图片描述

② filter

案例1:过滤集合总的偶数(java)

package cn.spark.study.core;

import org.apache.spark.SparkConf;
import org.apache.spark.api.java.JavaRDD;
import org.apache.spark.api.java.JavaSparkContext;
import org.apache.spark.api.java.function.Function;
import org.apache.spark.api.java.function.VoidFunction;
import java.util.Arrays;
import java.util.List;

public class Transfromation_7 {
   
    public static void main(String[] args) {
   
        myFilter();
    }
	private static void myFilter(){
   
        SparkConf conf = new SparkConf()
                .setAppName("map")
                .setMaster("local");
        //创建SparkContext
        JavaSparkContext sc = new JavaSparkContext(conf);

        //模拟结合
        List<Integer> numbers = Arrays.asList(1,2,3,4,5,6,7,8,9,10);

        //并行化集合,初始化RDD
        JavaRDD<Integer> numberRDD = sc.parallelize(numbers);
        //对初始RDD执行filter算子,将其中的偶数过滤出来
        //filter传入的也是faction,其他的输赢注意点,实际和map是一样的
        //每一个RDD初始化中的元素,都会传入call()方法,此时你可以执行各种自定义的计算逻辑
        //莱帕胺段这个元素石佛营是你想要的
        //如果你想要在新的RDD中保留这个元素,那么就返回true;否则,不想保留这个元素,返回false
        JavaRDD<Integer> filter = numberRDD.filter(new Function<Integer, Boolean>() {
   
            @Override
            public Boolean call(Integer integer) throws Exception {
   
                return integer % 2 == 0;
            }
        });

        filter.foreach(new VoidFunction<Integer>() {
   
            @Override
            public void call(Integer integer) throws Exception {
   
                System.out.println(integer);
            }
        });
        sc.close();
    }
}

在这里插入图片描述
案例2:过滤集合总的奇数(scala)

package cn.spark.study.core

import org.apache.spark.rdd.RDD
import org.apache.spark.{
   SparkConf, SparkContext}

object Transformation {
   
  def main(args: Array[String]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值