Spark练习之wordcount,基于排序机制的wordcount
Spark练习之wordcount
一、原理及其剖析
二、pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>spark</groupId>
<artifactId>com.spark</artifactId>
<version>1.0-SNAPSHOT</version>
<name>SparkTest</name>
<url>http://maven.apache.org</url>
<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<scala.version>2.10.0</scala.version>
<spark.version>1.3.0</spark.version>
<hadoop.version>2.6.4</hadoop.version>
<encoding>UTF-8</encoding>
</properties>
<dependencies>
<!-- scala依赖-->
<dependency>
<groupId>org.scala-lang</groupId>
<artifactId>scala-library</artifactId>
<version>${scala.version}</version>
</dependency>
<!-- spark依赖-->
<dependency>
<groupId>org.apache.spark</groupId>
<artifactId>spark-core_2.10</artifactId>
<version>${spark.version}</version>
</dependency>
<dependency>
<groupId>org.apache.spark</groupId>
<artifactId>spark-sql_2.10</artifactId>
<version>${spark.version}</version>
</dependency>
<!-- hivecontext要用这个依赖-->
<dependency>
<groupId>org.apache.spark</groupId>
<artifactId>spark-hive_2.10</artifactId>
<version>${spark.version}</version>
</dependency>
<!-- hadoop依赖-->
<dependency>
<groupId>org.apache.hadoop</groupId>
<artifactId>hadoop-client</artifactId>
<version>${hadoop.version}</version>
</dependency>
</dependencies>
<build>
<pluginManagement>
<plugins>
<!-- 编译scala的插件 -->
<plugin>
<groupId>net.alchim31.maven</groupId>
<artifactId>scala-maven-plugin</artifactId>
<version>3.2.2</version>
</plugin>
<!-- 编译java的插件 -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.5.1</version>
</plugin>
</plugins>
</pluginManagement>
<plugins>
<plugin>
<groupId>net.alchim31.maven</groupId>
<artifactId>scala-maven-plugin</artifactId>
<executions>
<execution>
<id>scala-compile-first</id>
<phase>process-resources</phase>
<goals>
<goal>add-source</goal>
<goal>compile</goal>
</goals>
</execution>
<execution>
<id>scala-test-compile</id>
<phase>process-test-resources</phase>
<goals>
<goal>testCompile</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<executions>
<execution>
<phase>compile</phase>
<goals>
<goal>compile</goal>
</goals>
</execution>
</executions>
</plugin>
<!-- 打包插件 -->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>2.4.3</version>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<filters>
<filter>
<artifact>*:*</artifact>
<excludes>
<exclude>META-INF/*.SF</exclude>
<exclude>META-INF/*.DSA</exclude>
<exclude>META-INF/*.RSA</exclude>
</excludes>
</filter>
</filters>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
**备注:此处会遇到坑,一定要将scala和spark的版本对应好,如果版本不对应,一个过高或一个过低,会导致程序无法正常运行。
三、使用Java进行spark的wordcount练习
import org.apache.spark.SparkConf;
import org.apache.spark.api.java.JavaPairRDD;
import org.apache.spark.api.java.JavaRDD;
import org.apache.spark.api.java.JavaSparkContext;
import org.apache.spark.api.java.function.FlatMapFunction;
import org.apache.spark.api.java.function.Function2;
import org.apache.spark.api.java.function.PairFunction;
import org.apache.spark.api.java.function.VoidFunction;
import scala.Tuple2;
import java.util.Arrays;
/**
* 使用Java开发本地测试的wordcount程序
*/
public class wordCount {
public static void main(String[] args) {
//编写Spark应用程序
//本地执行,直接在main方法执行
//第一步:创建SparkConf对象,设置Spark应用的配置信息
//使用setMaster()可以设置Spark应用程序要连接的Spark集群的master节点的url
//但是如果设置为local则代表在本地运行
SparkConf conf = new SparkConf()
.setAppName("workCount")
.setMaster("local");
//第二步:创建JavaSparkContext对象
//在Spark中,SparkContext是Spark所有功能的一个入口,你无论是用java,scala,甚至是python编写
//都必须要有一个SparkContext,它的主要作用,包括初始化Spark应用程序所需的一些核心组件,
//包括调度器(ADGSchedule、TaskScheduler),还会去到Spark Master节点上进行注册,等等。
//SparkContext,是Spark应用中,最重要的一个对象
//在spark中,编写不同类型的Spark应用程序,使用的SparkContext是不同的,
// 如果使用scala,使用的就是原生的SparkContext对象
//如果使用Java,那么就是JavaSparkContext对象
//如果是开发Spark SQL程序,那么就是SQLContext、HiveContext
//如果是Spark Streaming程序,那么就是它独有的SparkContext
//以此类推
JavaSparkContext sc = new JavaSparkContext(conf);
//第三步:要针对输入源(hdfs文件、本地文件,等等),创建一个初始的RDD。
//输入源中的数据会打散,分配到RDD的每个partition中,从而形成一个初始的分布式的数据集
//这里,进行本地测试,所以针对本地文件
//SparkContext中,用于根据文件类型的输入源创建RDD的方法,叫做textFile方法
//在Java中,创建的普通RDD,都叫做JavaRDD
//RDD中,有元素这种概念,如果是hdfs活着本地文件呢,创建的RDD,每一个元素就相当于是文件里的一行
JavaRDD<String> lines = sc.textFile("C://Users//10902//Desktop//spark.txt");
//第四步:对初始RDD进行transformation操作,也就是一些计算操作
//通常操作会通过创建function,并配合RDD的map、flagMap等算子来执行
//function,通常,如果比较简单,则创建指定Function的匿名内部类
//但是如果function比较复杂,则会单独创建一个类,作为实现这个function接口的类
//先将每一行拆分成单个的单词
//FlatMapFunction,有两个泛型参数,分别代表了输入和输出类型
//对于我本地的测试文件,输入肯定是String,因为是一行一行的文本,输出,也是String,因为是每一行的文本
//flagMap:其实就是,将RDD的一个元素,给拆分成一个或多个元素
JavaRDD<String> words = lines.flatMap(new FlatMapFunction<String, String>() {
private static final long serialVersionUID = 1L;
@Override
public Iterable<String> call(String line) throws Exception {
return Arrays.asList(line.split(" "));
}
});
//接着,需要将每一个单词,映射为(单词,1)的这种格式
//因为只有这样,才能根据单词作为key,来进行每个单词的出现次数的累加
//mapToPair,其实就是将每个元素,映射为一个(v1,v2)这样的Tuple2类型的元素
//tuple2是scala类型,包含了两个值
//mapToPair这个算子,要求的是与PairFunction配合使用,第一个泛型参数代表了输入类型
//第二个和第三个泛型参数,代表的输入的Tuple2的第一个值和第二个值的类型
//JavaPairRdd的两个泛型参数,分别代表了tuple元素的第一个值和第二个值的类型
JavaPairRDD<String, Integer> pairs = words.mapToPair(
new PairFunction<String, String, Integer>() {
private static final long serialVersionUID = 1L;
@Override
public Tuple2<String, Integer> call(String word) throws Exception {
return new Tuple2<String, Integer>(word, 1);
}
}
);
//接着,需要以单词作为key,统计每个单词出现的次数
//这里要使用reduceByKey这个算子,对每个key对应的value,都进行reduce操作
//比如JavaPairRdd中有个元素,分别为(hello,1)(hello,1)(hello,1)(world,1)
//reduce操作,相当于是把第一个值和第二个值进行计算,然后再将结果与第三个值进行计算
//比如这里的hello,那么就相当于是,首先1 + 1 = 2 ,然后再将2 + 1 = 3
//最后返回的JavaPairRDD中的元素,也是tuple,但是第一个值就是每个key,第二个值就是key的value
//reduce之后的结果,相当于就是每个单词出现的次数
JavaPairRDD<String, Integer> wordCounts = pairs.reduceByKey(
new Function2<Integer, Integer, Integer>() {
private static final long serialVersionUID = 1L;
@Override
public Integer call(Integer integer, Integer integer2) throws Exception {
return integer + integer2;
}
}
);
//到这里为止,我们通过几个spark算子操作,以及统计出了单词的次数
//但是,之前我们使用的flatMap、mapToPair、reduceByKey这种操作,都叫做transformation操作
//一个spark应用中,光是有transformation操作,是不行的,是不会执行的,必须要有一种叫做action
//最后,使用一种叫做action操作的,比如说,foreach,来触发程序的执行
wordCounts.foreach(new VoidFunction<Tuple2<String, Integer>>() {
@Override
public void call(Tuple2<String, Integer> wordCount) throws Exception {
System.out.println(wordCount._1 + " 出现了" + wordCount._2 + " 次");
}
});
sc.close();
}
}
四、使用scala进行spark的wordcount练习
import org.apache.spark.{SparkConf, SparkContext}
object WordCount {
def main(args: Array[String]): Unit = {
/**
* 第一步:创建Spark的配置对象SparkConf,设置Spark程序运行时的配置信息,
* 例如说通过设置setMaster来设置程序要链接的Spark集群的Master的URL,
* 如果设置为local,则代表Spark程序在本地运行。
*/
val conf = new SparkConf //创建SparkConf对象
conf.setAppName("WordCount") //设置应用程序的名称,在程序运行的监控界面可以看到名称
conf.setMaster("local") //此时,程序在本地运行,不需要安装Spark集群
/**
* 第二步:创建SparkContext对象
* SparkContext是Spark程序所有功能的唯一入口,无论是采用scala、java、Python,R等都
* 必须有一个SparkContext。SparkContext核心作用:初始化Spark应用程序运行所需要的核心组件,包括
* DAGScheduler,TaskScheduler、SchedulerBackend同时还会负责Spark程序往Master注册程序等。
* SparkContext是这个Spark程序中最为至关重要的一个对象。
*/
val sc = new SparkContext(conf)
/**
* 第三步:根据具体的数据源(HDFS、HBase、Local FS、DB、S3等)通过SparkContext创建RDD。
* RDD的创建方式有三种:根据外部的数据源(HDFS)、根据Scala集合、其他的RDD操作。数据会被RDD划分成一系列的
* Partitions,分配到每个Partition的数据属于一个Task的处理范畴
*/
val lines = sc.textFile("C://Users//10902//Desktop//spark.txt", 1) //
/**
* 第四步:对初始化的RDD进行Transformation级别处理,例如map、filter等高阶函数等的编程,来进行具体的数据计算。
*/
/**
* 4.1、对每一行的字符串拆分成单个的单词
*/
val words = lines.flatMap { line => line.split(" ") } //对每一行的字符串进行单词拆分并把所有行的拆分结果通过flat合并成为一
/**
* 4.2、在单词拆分的基础上对每个单词实例计数为1,也就是word => (word,1)
*/
val pairs = words.map { word => (word, 1) }
/**
* 4.3、在每个单词实例计数为1基础之上统计每个单词在文件中出现的总次数
*/
val wordCounts = pairs.reduceByKey(_ + _) //对相同的key,进行value的累计
wordCounts.foreach(map => println(map._1 + ":" + map._2))
sc.stop()
}
}
五、基于排序机制的wordcount
import org.apache.spark.{SparkConf, SparkContext}
object ScalaSortWordCount {
def main(args: Array[String]) {
val conf = new SparkConf //创建SparkConf对象
conf.setAppName("ScalaSortWordCount") //设置应用程序的名称,在程序运行的监控界面可以看到名称
conf.setMaster("local") //此时,程序在本地运行,不需要安装Spark集群
val sc = new SparkContext(conf)
val lines = sc.textFile("C://Users//xxx//Desktop//spark.txt", 1)
val words = lines.flatMap { line => line.split("") }
val pairs = words.map { word => (word, 1) }
val wordCounts = pairs.reduceByKey(_ + _)
val countWords = wordCounts.map { wordCount => (wordCount._2, wordCount._1) }
val sortedCountWords = countWords.sortByKey(false)
val sortedWordCounts = sortedCountWords.map { sortedCountWord => (sortedCountWord._2, sortedCountWord._1) }
sortedWordCounts.foreach(sortWordCount => println(sortWordCount._1 + "出现了:" + sortWordCount._2 + "次"))
}
}
Spark练习之wordcount,基于排序机制的wordcount的更多相关文章
- 09、高级编程之基于排序机制的wordcount程序
package sparkcore.java; import java.util.Arrays; import java.util.Iterator; import org.apache.spark. ...
- 55、Spark Streaming:updateStateByKey以及基于缓存的实时wordcount程序
一.updateStateByKey 1.概述 SparkStreaming 7*24 小时不间断的运行,有时需要管理一些状态,比如wordCount,每个batch的数据不是独立的而是需要累加的,这 ...
- Hive数据分析——Spark是一种基于rdd(弹性数据集)的内存分布式并行处理框架,比于Hadoop将大量的中间结果写入HDFS,Spark避免了中间结果的持久化
转自:http://blog.csdn.net/wh_springer/article/details/51842496 近十年来,随着Hadoop生态系统的不断完善,Hadoop早已成为大数据事实上 ...
- Spark 颠覆 MapReduce 保持的排序记录
在过去几年,Apache Spark的採用以惊人的速度添加着,通常被作为MapReduce后继,能够支撑数千节点规模的集群部署. 在内存中数 据处理上,Apache Spark比MapReduce更加 ...
- Spark Streaming揭秘 Day27 Job产生机制
Spark Streaming揭秘 Day27 Job产生机制 今天主要讨论一个问题,就是除了DStream action以外,还有什么地方可以产生Job,这会有助于了解Spark Streaming ...
- Spark Tungsten in-heap / off-heap 内存管理机制--待整理
一:Tungsten中到底什么是Page? 1. 在Spark其实不存在Page这个类的.Page是一种数据结构(类似于Stack,List等),从OS层面上讲,Page代表了一个内存块,在Page里 ...
- 输入DStream之基础数据源以及基于HDFS的实时wordcount程序
输入DStream之基础数据源以及基于HDFS的实时wordcount程序 一.Java方式 二.Scala方式 基于HDFS文件的实时计算,其实就是,监控一个HDFS目录,只要其中有新文件出现,就实 ...
- Android的事件处理机制(一)------基于回调机制的事件处理
Android平台的事件处理机制有两种,一种是基于回调机制的,一种是基于监听接口的,现介绍第一种:基于回调机制的事件处理.Android平台中,每个View都有自己的处理事件的回调方法,开发人员可以通 ...
- Spark Streaming揭秘 Day16 数据清理机制
Spark Streaming揭秘 Day16 数据清理机制 今天主要来讲下Spark的数据清理机制,我们都知道,Spark是运行在jvm上的,虽然jvm本身就有对象的自动回收工作,但是,如果自己不进 ...
随机推荐
- 仿小米logo案例
效果:做一个具有logo能过渡切换效果,类似于小米网站的logo 思路:将两个用于切换的logo以文字形式嵌入活动块banner的左右半,活动块banner的上级是主展示块box,初态只展示右半log ...
- spark:distinct算子实现原理
distinct的底层使用reducebykey巧妙实现去重逻辑 //使用reduceByKey或者groupbykey的shuffle去重思想rdd.map(key=>(key,null)). ...
- Windows下使用Graalvm将Javafx应用编译成exe
1 背景 Graalvm是Oracle推出的一款新型虚拟机,其中一个吸引人的功能是:它可以将Java代码编译成各个平台的本地代码,这些平台包括:linux.macOS.windows.iOS.andr ...
- 如何优雅地开发HarmonyOS APP应用
目录: 一.挖掘项目需求或者做项目移植 二.创建项目工程 三.功能模块实现的流程思路 四.养成良好的编程规范习惯以及运用设计模式 研究HarmonyOS有一段时间了,今天主要结合自己多年的项目开发经验 ...
- PAT甲级 1155 Heap Paths (30分) 堆模拟
题意分析: 给出一个1000以内的整数N,以及N个整数,并且这N个数是按照完全二叉树的层序遍历输出的序列,输出所有的整条的先序遍历的序列(根 右 左),以及判断整棵树是否是符合堆排序的规则(判断是大顶 ...
- wpf 通过为DataGrid所绑定的数据源类型的属性设置Attribute改变DataGrid自动生成列的顺序
环境Win10 VS2019 .Net Framework4.8 在wpf中,如果为一个DataGrid绑定到一个数据源,默认情况下DataGrid会为数据源类型的每个属性生成一个列(Column)对 ...
- spring cloud gateway 日志打印
从api请求中获取访问的具体信息,是一个很常见的功能,这几天在研究springcloud,使用到了其中的gateway,刚好将研究的过程结果都记录下来 0. Version <parent> ...
- 【Java】运算符(算术、赋值、比较(关系)、逻辑、条件、位运算符)
运算符 文章目录 运算符 1. 算术运算符 2. 赋值运算符 3. 比较运算符 4. 逻辑运算符 5. 条件运算符 6. 位运算符 7. 运算符优先级 8. 运算符操作数类型说明 9.code 算术运 ...
- Head First 设计模式 —— 15. 与设计模式相处
模式 是在某情境(context)下,针对某问题的某种解决方案. P579 情景:应用某个模式的情况 问题:你想在某情境下达到的目标,但也可以是某情境下的约束 解决方案:一个通用的设计,用来解决约束. ...
- 【对线面试官】Java多线程基础
// 请求直接交给线程池来处理 public void push(PushParam pushParam) { try { pushServiceThreadExecutor.submit(() -& ...