sparkcore

spark-shell交互式工具

  • 启动Spark-Shell
 
 
  1. ./bin/spark-shell
  2. ./spark-shell --master
  3. ./bin/spark-shell --master local[2] //使用两个线程运行
  4. ./bin/spark-shell --master local[2] --jar test.jar //使用两个线程运行指定Jar包
  5. ./bin/spark-shell --master local --master spark://spark01:7077 //使用standalone模式

在spark-Shell(命令行)中,已经创建了一个名为sc的SparkContext对象 
—master用来设置context将要连接并使用的资源主节点,master的值可以是Standalone模式的Spark集群地址,Mesos或Yarn集群的URL,或者是一个local地址 
使用jar可以添加Jar包的路径,使用逗号乐意添加多个包 
Spark_Shell的本质是在后台调用了spark-submit脚本来启动应用程序

  • Spark-Shell操作 
    数据收集后,需要对数据进行一系列的处理,包括数据的抽取-转换-装载(Extract-Transform-Load,ETL),数据统计,数据挖掘,以及后续的数据呈现和为决策而提供的数据持久化 
    //加载HDFS文件和本地文件都是使用textFile(),区别是前缀进行标志(hdfs://或file:///) 
    从本地读取的文件返回MapPartitionsRDD。从hdfs中读取的文件先转换成HadoopRDD,然后隐式转换为MapPatitionRDD 
    MapPatitionRDD和HadoopRDD都是基于Spark的弹性分布式数据集RDD
 
 
  1. //加载文件
  2. val aa=sc.textFile("File:///home/aa/bb/WCDemo.txt")
  3. val aa=sc.textFile("hdfs://spark01:9000/WCDemo.txt")
  4. //包含指定关键字的行数
  5. val result=aa.filter(line=>line.contains("spark"))
  6. result.count
  7. val result=aa.filter(line=>line.contains("spark")).count()
  8. //获取有指定关键字的行的全部内容
  9. val result=aa.filter(_.contains("spark")).collect()
  10. //获取RDD文件的第一行
  11. aa.first()
  12. //获取RDD文件的行数
  13. aa.count()
  14. //找出文本中单词个数最多的那行的单词数
  15. //首先将aa的每一行文本使用split进行切分,并统计切分后每行的单词数,然后执行reduce操作,用(a,b)=>if(a>b) a else b 进行比较,返回最大值
  16. aa.map(line=>line.split("\t").size).reduce((a,b)=>if(a>b) a else b)
  17. //词频统计
  18. //结合flatMap,Map和reduceByKey来计算文件中每个单词的词频,并返回(String,Int)类型的键值对shuffleRDD,最后使用collection聚合单词计数结果
  19. val wordCount=aa.flatMap(line=>line.split("\t")).map(word=>(word,1)).reduceByKey((x,y)=>x+y).collect()
  20. //使用占位符(_)当每个参数在函数文本中最多出现一次的时候,可以使用_+_扩展成带两个参数的函数文本,多个下划线指带多个参数,而不是单个参数重复使用(第一个下划线代表第一个参数,第二个下划线代表第二个参数)
  21. val wordCount=aa.flatMap_.split(" ")).map((_,1)).reduceByKey(_+_)
  22. //Spark默认是不进行排序的,可以使用sortByKey按照Key进行排序,false为降序,true为升序
  23. //map(m=>(m._2,m._1)) 实现了Key和Value互换
  24. val wordCount=aa.flatMap(_.split("\t")).map((_,1)).reduceByKey(_+_).map(m=>(m._1,m._2)).sortByKey(false).map(m=>(m._2,m._1)).collect()
  25. //保存文件
  26. wordCount.saveAsTextFile("hdfs://spark01:9000/out/WCDemoOUT.txt")
  1. RDD缓存 
    Spark支持将数据结构存进缓存种,当数据被反复访问时,是非常有用的
 
 
  1. result.cache()
  2. result.persist()
  3. result.unpersist()

spark context与部署模式

 
 
  1. //创建SparkConf,alt+enter,快速导包
  2. val conf = new SparkConf().setAppName("WCDemo.txt").setMaster("local")
  3. //创建sparkContext对象
  4. val sc = new SparkContext(conf)
  5. //从HDFS中读取数据
  6. val lines=sc.textFile("hdfs://spark01/WCDemo.txt")
  7. //分隔获取每个单词
  8. val words=lines.flatMap(_.split("\t"))
  9. //将每个单词设置1次
  10. val psirs=WCDemo.map(word=>(word,1))
  11. //统计每个单词出现的次数
  12. val wordsCount=pairs.reduceByKey(_+_)

保存结果到HDFS

 
 
  1. wordsCount.saveAsTextFile("hdfs://spark01/WCReduce")

输出

 
 
  1. result.collect()
  2. //通过foreach算子输出单词与次数
  3. result.foreach(x=>println(x._1+" "+x._2))
  • 案例——WordCount
 
 
  1. /**
  2. * 用Java开发Spark的WordCount
  3. * @author Administrator
  4. */
  5. public class WordCount {
  6. public static void main(String[] args) {
  7. //第一步:创建SparkConf对象
  8. //set master()用于设置运行的Master的URL
  9. //如果要是在本地运行,需要设置为local或local[N](N>2)
  10. //如果程序需要打包在集群中运行,就不需要设置Master
  11. SparkConf conf=new SparkConf().setAppName("WordCount").setMaster("local");
  12. //第二步:创建JavaSparkContext对象
  13. // SparkContext,即为Spatj上下文,它包含在Driver驱动程序中
  14. //Spark程序的运行离不开SparkContext
  15. // Scala开发Spark对应的是SparkContext
  16. //Java开发Spark对应的是JavaSparkContext
  17. // 创建SparkContext对象时,需要SparkConf对象作为参数
  18. JavaSparkContext sc = new JavaSparkContext(conf);
  19. //第三步:从HDFS中加载数据,生成JavaRDD<String>
  20. //从hdfs等外部数据源创建程序中的第一个RDD,即为初始RDD
  21. //创建初始RDD有两种方式
  22. //第一种:通过HDFS等外部数据源中创建
  23. //第二种:通过并行集合的方式创建
  24. //val array=Array(1,2,3,4,5)
  25. //val rdd=sc.parallelize(array)
  26. JavaRDD<String> lines = sc.textFile("hdfs://tgmaster:9000/in/resws");
  27. //第四步:分隔单词
  28. //flatMap:flatten map,先map后flatten
  29. //flatMap算子中,通常有一个String类型的参数,同时具有Iterable<T>集合类型的返回值
  30. JavaRDD<String> words = lines.flatMap(new FlatMapFunction<String, String>() {
  31. private static final long serialVersionUID = 1L;
  32. public Iterable<String> call(String line) throws Exception {
  33. return Arrays.asList(line.split(" "));
  34. }
  35. });
  36. //第五步:将分隔后的每个单词出现次数记录为1,形成键值对<单词,1>
  37. //用java开发spark,如果需要通过映射的方式产生键值对,此时要到到mapToPair算子
  38. //scala中只有map算子(没有mapToPair)
  39. //mapToPair:使用映射,并产生键值对
  40. //map:使用映射,不产生键值对
  41. //mapToPair算子中有一个String类型的参数,返回值是Tuple2<String, Integer>
  42. avaPairRDD<String, Integer> pairs = words.mapToPair(new PairFunction<String, String, Integer>() {
  43. private static final long serialVersionUID = 1L;
  44. public Tuple2<String, Integer> call(String word) throws Exception {
  45. return new Tuple2<String, Integer>(word, 1);
  46. }
  47. });
  48. //第六步:通过reduceByKey()算子统计每个单词出现的次数
  49. //reduceByKey算子有两个Integer类型的参数,返回值是Integer
  50. //运行过程是,现在本地按照Key值进行聚合,然后在全局范围内进行聚合
  51. //性能比groupByKey强很多
  52. avaPairRDD<String, Integer> result = pairs.reduceByKey(new Function2<Integer,Integer, Integer>() {
  53. private static final long serialVersionUID = 1L;
  54. public Integer call(Integer num1, Integer num2) throws Exception {
  55. return num1+num2;
  56. }
  57. });
  58. //第七步:通过foreach()算子输出最终结果
  59. result.foreach(new VoidFunction<Tuple2<String,Integer>>() {
  60. private static final long serialVersionUID = 1L;
  61. public void call(Tuple2<String, Integer> info) throws Exception {
  62. System.out.println(info._1+"出现了"+info._2);
  63. }
  64. });
  65. }
  66. }
  67. //IDEA
  68. import org.apache.spark.{SparkConf, SparkContext}
  69. object wordcount {
  70. def main(args: Array[String]): Unit = {
  71. val conf = new SparkConf().setAppName("asd").setMaster("local")
  72. val sc = new SparkContext(conf)
  73. val lines= sc.textFile("hdfs://spark01:9000/WCDemo.txt")
  74. val words=lines(_.split("\t"))
  75. val pairs=words.map(word=>(word,1))
  76. val wordsCount=pairs.reduceByKey(_+_)
  77. wordsCount.saveAsTextFile("hdfs://spark01:9000/WCout.txt")
  78. }
  79. }
  • spark部署模式 
    Local本地模式
 
 
  1. //执行需要用到CPU的两个核
  2. spark-shell --master local[2]

运行与本地 
Standalone独立模式 
1.spark自带的一种集群模式,自己管理集群资源,只要将hadoop的HDFS启动 
2.master节点有master,slave节点有worker 
3.启动./bin/spark-shell –master spark://master:7077 
Yarn模式 
1.spark自己不管理资源,向Yarn申请资源,所以保证Yarn必须启动起来 
2.操作步骤

  • 启动hadoop:在hadoop目录执行start-all.sh
  • 到spark目录,./bin/spark-shell –master yarn-client(yarn-cluster)
    • IDEA生成Jar包 
      1.File——>project Structure,弹出“project Structure”的设置对话框 
      2.选择左边的Artifacts,点击上方的“+” 
      3.选择Jar——>from moduls with dependencies 
      4.选择要启动的类,选择确定 
      5.应用之后选择菜单“build”——>“build Artifact”,选择build或Rebuild即可生成
    • 上传jar包
 
 
  1. ./spark-submit \
  2. --class Test.wordcount \ //包名.类
  3. --master yarn--cluster \
  4. /home/lyuc/Myspark.jar //地址
  • Master URL格式及说明 

RDD弹性分布式数据集

  • RDD在抽象上来说是一种元素集合,包含了数据,可以被分为多个区,每个分区分布在集群的不同节点上,从而让HDFS的数据可以被操作,
  • RDD通常通过Hadoop上的文件,即HDFS或Hive表来进行创建,也可以通过程序中的集合创建
  • RDD最重要的特性是,提供容错性,可以自动从节点失败中恢复过来,如果某个节点上的RDD partition,因为节点故障,导致数据丢了,那么RDD会自动通过书籍来源重新计算该partition
  • 数据默认放在内存中,在内存不足是,Spark会自动将RDD写入磁盘中

RDD定义

一个RDD包含5个核心属性

  1. 一个分区表,每个分区是RDD的一部分数据(数据块)
  2. 一个依赖列表,存储依赖的其他RDD
  3. 一个名为computer的计算函数,用于计算RDD多各分区的值
  4. 分区器(可选)用于键值类型的RDD,比如某个RDD是按散列来分区的 
    5.计算各分区器是优先的位置列表(可选)比如HDFS上的文件生成RDD时,RDD分区的位置优先选择数据所在的节点

创建RDD

  • 并行化集合创建RDD 
    针对程序中的集合调用sparkcontext的parallelize()方法 
    Spark会将集合中的数据拷贝到集群上去, 形成一个分布式的数据集合, 也就是一个RDD。相当于集合中的一部分数据会到一个节点上, 而另一部分数据会到其他节点上, 然后就可以用并行的方式来操作这个分布式数据集合, 即RDD。
 
 
  1. // 并行化集合创建RDD
  2. val arr = Array(1,2,3,4,5)
  3. //没有指定RDD分区,默认微程序所分配的资源的CPU核数
  4. val rdd=sc.parallelize(arr)
  5. val sum=rdd.reduce(_+_)
  • 使用本地文件和HDFS创建RDD 
    spark支持使用任何hadoop支持的存储系统上的文件创建RDD,通过调用SparkContext()的textFile()方法。可以针对本地文件或HDFS文件创建RDD 
    *spark的textfile()方法致辞针对目录,压缩文件以及通配符进行RDD创建目录 
    *spark会默认为HDFS文件的每一个block创建一个partition,但是也可以通过textFile()的第二个参数手动设置分区数,只能比block多,不能少
 
 
  1. //制定了lines中有两个分区
  2. //设置了分区数只能比block多
  3. val lines=sc.textFile("hdfs路径"2)
  4. val wordCount=rdd.map(line=>line.length).reduce(_+_)

spark的textFile()还有一些特例方法来创建RDD

  1. SparkContext.wholeTextFile() 
    针对一个目录中的大量小文件,返回组成的pair,作为PairRDD,不是普通RDD,普通RDD中每个元素就是文件中的一行文本
  2. SparkContext.sequenceFilek,v 
    可以针对SequenceFile创建RDD,K和V泛型类型就是SequenceFile的key和value的类型。 K和V要求必须是 
    Hadoop的序列化类型, 比如IntWritable、 Text等。
  3. SparkContext.hadoopRDD() 
    对于Hadoop的自定义输入类型, 可以创建RDD。 该方法接收JobConf、 InputFormatClass、 Key和Value的Class。
  4. SparkContext.objectFile() 
    可以针对之前调用RDD.saveAsObjectFile()创建的对象序列化的文件, 反序列化文件中的数据, 并创建一个RDD。
  • 通过Transformation(转化)类型的算子产生新的RDD
 
 
  1. val result=lines.flatMap(_.split(" ")).map((_.1)).reduceBykey(_+_)
  2. //result.collect,result.foreach(println _)行动类型算子

RDD操作

  • 创建操作
  • 转换操作(transformation) 
    在spark中关于transformation类型的算子,系统只是记录下了操作行为,但行为没有执行,当程序遇到一个Action型的算子时,会触发job的提交运行(lazy特性),此时Action之前的transformation类型算子会被执行 

  • 行动操作(action)

  • 控制操作 
    缓存到内存,也称内存持久化
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值