Spark知识点总结

1.什么是spark?
spark是基于内存计算的通用大数据并行计算框架,是一个快速、通用可扩展的大数据分析引擎。它给出了大一统的软件开发栈,适用于不同场合的分布式场景,如批处理、迭代算法、交互式查询、流处理、机器学习和图计算。
2.Spark生态系统?
SparkCore:spark的核心计算 主要Rdd
SparkSQL:提供了类sql方式操作结构化半结构化数据。对历史数据进行交互式查询。(即席查询:用户根据自己的需求,自定义查询)

SparkStreaming:提供了近乎实时的流式数据处理,与storm相比有更高的吞吐量。(实时计算 目前实时计算框架有哪些? storm、sparkstreaming、flink)

SparkMl:提供了常见的机器学习算法库,包括分类、回归、聚类、协同工过滤(个性推荐:用户画像)等,还提供模型评估、数据处理等额外功能,使得机器学习能够更加方便的在分布式大数据环境下,快速的对数据进行处理形成模型后提供在线服务。

Graphx:用来操作图的程序库,可以进行并行的图计算。支持各种常见的图算法,包括page rank、Triangle Counting等。
3.常见的 分布式文件系统?
hdfs fastdfs Tachyon TFS GFS S3
4.master资源分配有哪些?
尽量集中 尽量打散
1.Application的调度算法有两种,一种是spreadOutApps,另一种是非spreadOutApps。

2.spreadOutApps,会将每个Application要启动的executor都平均分配到各个worker上去。(比如有10个worker,20个cpu core要分配,那么实际会循环两遍worker,每个worker分配一个core,最后每个worker分配了2个core,这里的executor数量可能会与spark-submit设置的不一致)

3.非spreadOutApps,将每个Application尽可能分配到尽量少的worker上去。(比如总共有10个worker,每个有10个core,app总共要分配20个core,其实只会分配到两个worker上,每个worker占满10个core,其余app只能分配到下一个worker,这里的executor数量可能会与spark-submit设置的不一致)
5.spark 可以代替hadoop 吗?
spark会替代Hadoop的一部分,会替代Hadoop的计算框架,如mapReduce、Hive查询引擎,但spark本身不提供存储,所以spark不能完全替代Hadoop。
6.spark 特点?
6.1 速度快
Spark 使用DAG 调度器、查询优化器和物理执行引擎,能够在批处理和流数据获得很高的性能。根据官方的统计,它的运算速度是hadoop的100x倍
6.2 使用简单
Spark的易用性主要体现在两个方面。一方面,我们可以用较多的编程语言来写我们的应用程序,比如说Java,Scala,Python,R 和 SQL;另一方面,Spark 为我们提供了超过80个高阶操作,这使得我们十分容易地创建并行应用,除此之外,我们也可以使用Scala,Python,R和SQL shells,以实现对Spark的交互
6.3 通用性强
与其说通用性高,还不如说它集成度高,如图所示:以Spark为基础建立起来的模块(库)有Spark SQL,Spark Streaming,MLlib(machine learning)和GraphX(graph)。我们可以很容易地在同一个应用中将这些库结合起来使用,以满足我们的实际需求。
6.4 到处运行
Spark应用程度可以运行十分多的框架之上。它可以运行在Hadoop,Mesos,Kubernetes,standalone,或者云服务器上。它有多种多种访问源数据的方式。可以用standalone cluster模式来运行Spark应用程序,并且其应用程序跑在Hadoop,EC2,YARN,Mesos,或者Kubernates。对于访问的数据源,我们可以通过使用Spark访问HDFS,Alluxio,Apache Cassandra,HBase,Hive等多种数据源。
7.DAG

有向无环图
"有向"指的是有方向,准确的说应该是同一个方向,"无环"则指够不成闭环。在DAG中,没有区块的概念,他的组成单元是一笔笔的交易,每个单元记录的是单个用户的交易,这样就省去了打包出块的时间。验证手段则依赖于后一笔交易对前一笔交易的验证,换句话说,你要想进行一笔交易,就必须要验证前面的交易,具体验证几个交易,根据不同的规则来进行。这种验证手段,使得DAG可以异步并发的写入很多交易,并最终构成一种拓扑的树状结构,能够极大地提高扩展性。

8.spark 开发语言选择?
java scala python
9.什么是Rdd?
Spark 中最基本的数据抽象是 RDD。

RDD:弹性分布式数据集 (Resilient Distributed DataSet)。
RDD 有三个基本特性

这三个特性分别为:分区,不可变,并行操作。
a, 分区

每一个 RDD 包含的数据被存储在系统的不同节点上。逻辑上我们可以将 RDD 理解成一个大的数组,数组中的每个元素就代表一个分区 (Partition) 。

在物理存储中,每个分区指向一个存储在内存或者硬盘中的数据块 (Block) ,其实这个数据块就是每个 task 计算出的数据块,它们可以分布在不同的节点上。

所以,RDD 只是抽象意义的数据集合,分区内部并不会存储具体的数据,只会存储它在该 RDD 中的 index,通过该 RDD 的 ID 和分区的 index 可以唯一确定对应数据块的编号,然后通过底层存储层的接口提取到数据进行处理。

在集群中,各个节点上的数据块会尽可能的存储在内存中,只有当内存没有空间时才会放入硬盘存储,这样可以最大化的减少硬盘 IO 的开销。
b,不可变

不可变性是指每个 RDD 都是只读的,它所包含的分区信息是不可变的。由于已有的 RDD 是不可变的,所以我们只有对现有的 RDD 进行转化 (Transformation) 操作,才能得到新的 RDD ,一步一步的计算出我们想要的结果。

这样会带来这样的好处:我们在 RDD 的计算过程中,不需要立刻去存储计算出的数据本身,我们只要记录每个 RDD 是经过哪些转化操作得来的,即:依赖关系,这样一方面可以提高计算效率,一方面是错误恢复会更加容易。如果在计算过程中,第 N 步输出的 RDD 的节点发生故障,数据丢失,那么可以根据依赖关系从第 N-1 步去重新计算出该 RDD,这也是 RDD 叫做"弹性"分布式数据集的一个原因。
c,并行操作

因为 RDD 的分区特性,所以其天然支持并行处理的特性。即不同节点上的数据可以分别被处理,然后生成一个新的 RDD。
10.Rdd的属性?

  • 1) A list of partitions

一个分区列表,一个rdd有多个分区,后期spark任务计算是以分区为单位,一个分区就对应上一个task线程。 通过val rdd1=sc.textFile(文件) 如果这个文件大小的block个数小于等于2,它产生的rdd的分区数就是2 如果这个文件大小的block个数大于2,它产生的rdd的分区数跟文件的block相同

  • 2)A function for computing each split

由一个函数计算每一个分片 比如: rdd2=rdd1.map(x=>(x,1)) ,这里指的就是每个单词计为1的函数

  • 3)A list of dependencies on other RDDs

一个rdd会依赖于其他多个rdd,这里就涉及到rdd与rdd之间的依赖关系,后期spark任务的容错机制就是根据这个特性而来。 比如: rdd2=rdd1.map(x=>(x,1)) rdd2的结果是通过rdd1调用了map方法生成,那么rdd2就依赖于rdd1的结果 对其他RDD的依赖列表,依赖还具体分为宽依赖和窄依赖,但并不是所有的RDD都有依赖。

  • 4)Optionally, a Partitioner for key-value RDDs (e.g. to say that the RDD is hash-partitioned)

(可选项) 对于kv类型的rdd才会有分区函数(必须要产生shuffle),对于不是kv类型的rdd分区函数是None。 分区函数的作用:它是决定了原始rdd的数据会流入到下面rdd的哪些分区中。 spark的分区函数有2种:第一种hashPartitioner(默认值), 通过 key.hashcode % 分区数=分区号 第二种RangePartitioner,是基于一定的范围进行分区。

  • 5)Optionally, a list of preferred locations to compute each split on (e.g. block locations for an HDFS file)

(可选项) 一组最优的数据块的位置,这里涉及到数据的本地性和数据位置最优 spark后期在进行任务调度的时候,会优先考虑存有数据的worker节点来进行任务的计算。大大减少数据的网络传输,提升性能。
11.分片的个数由什么决定?

默认 手动 hdfs kafka

text文件分片(sc.textFile为例):

def textFile(
  path: String,
  minPartitions: Int = defaultMinPartitions): RDD[String] = withScope {
assertNotStopped()
hadoopFile(path, classOf[TextInputFormat]  /* 数据文件的输入格式 :org.apache.hadoop.mapred.TextInputFormat */
, classOf[LongWritable], classOf[Text],
  minPartitions).map(pair => pair._2.toString).setName(path)
}
 hadoopFile方法生成HadoopRDD
 HadoopRDD(
  this,
  confBroadcast,
  Some(setInputPathsFunc),
  inputFormatClass,
  keyClass,
  valueClass,
  minPartitions) /* minPartitions为生成该RDD的最小分片数,表示该RDD的分片数最小值,默认为2*/
  .setName(path)

在执行action方法(如count)时,spark应用才真正开始计算,通过调用rdd.partitions.length计算出分片数

    def runJob[T, U: ClassTag](rdd: RDD[T], func: Iterator[T] => U): Array[U] = {
runJob(rdd, func, 0 until rdd.partitions.length)
}

通过跟踪该方法可以看出该函数最终会调用到HadoopRDD的getPartitions方法,在该方法中通过inputFormat的getSplit方法计算分片数

    getInputFormat(jobConf).getSplits(jobConf, minPartitions)

TextInputFormat继承至FileInputFormat,FileInputFormat的getSplit方法网上有许多分析,这里不再展开,大致的原理是根据文件个数,传入的minpartitions,mapreduce.input.fileinputformat.split.minsize等参数计算出分片数。

hbase表分片

在读取HBase数据时,没有类似textFile的接口的封装,可调用如下接口生成给予hbase数据的RDD,

val hBaseRDD = sc.newAPIHadoopRDD(conf, 
classOf[TableInputFormat], /*该类的全类名为:  org.apache.hadoop.hbase.mapreduce.TableInputFormat */
  classOf[org.apache.hadoop.hbase.io.ImmutableBytesWritable],  
  classOf[org.apache.hadoop.hbase.client.Result])  
  
  该方法生成new NewHadoopRDD(this, fClass, kClass, vClass, jconf)

在执行action操作时,同样调用到rdd.partitions方法,跟踪至newHadoopRDD之后,发现调用到

inputFormat.getSplits(new JobContextImpl(_conf, jobId))

查看对应的getSplits方法可以看出:

默认情况下(hbase.mapreduce.input.autobalance的值为false)hbase表如果存在多个region,则每个region设置为一个split。

如果设置了开启均衡(设置hbase.mapreduce.input.autobalance的值为true:在hbase的region大小不均衡引发的数据倾斜,将导致不同的region处理耗时较多,该参数为了解决此场景),则会在每个region对应一个split的基础上,将较小(小于平均大小)的region进行合并作为一个split,较大(大于平均size的三倍(其中三可配置))的region拆分为两个region。

   splits伪代码如下(源码可参考TableInputFormatBase.calculateRebalancedSplits):
    
    while ( i < splits.size)
    {
        if(splits(i).size > averagesize * 3) {
        if(! splitAble)
            resultsplits.add(split(i))
        else{
  
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值