千家信息网

关于Spark拷问的5个问题分别是什么

发表于:2026-11-02 作者:千家信息网编辑
千家信息网最后更新 2026年11月02日,这篇文章给大家介绍关于Spark拷问的5个问题分别是什么,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。1.Spark计算依赖内存,如果目前只有10g内存,但是需要将500G的文件
千家信息网最后更新 2026年11月02日关于Spark拷问的5个问题分别是什么

这篇文章给大家介绍关于Spark拷问的5个问题分别是什么,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。

1.Spark计算依赖内存,如果目前只有10g内存,但是需要将500G的文件排序并输出,需要如何操作?

①、把磁盘上的500G数据分割为100块(chunks),每份5GB。(注意,要留一些系统空间!)

②、顺序将每份5GB数据读入内存,使用quick sort算法排序。

③、把排序好的数据(也是5GB)存放回磁盘。

④、循环100次,现在,所有的100个块都已经各自排序了。(剩下的工作就是如何把它们合并排序!)

⑤、从100个块中分别读取5G/100=0.05 G入内存(100input buffers)。

⑥、执行100路合并,并将合并结果临时存储于5g基于内存的输出缓冲区中。当缓冲区写满5GB时,写入硬盘上最终文件,并清空输出缓冲区;当100个输入缓冲区中任何一个处理完毕时,写入该缓冲区所对应的块中的下一个0.05 GB,直到全部处理完成。

2.countByValue和countByKey的区别

首先从源码角度来看:

// PairRDDFunctions.scala
def countByKey(): Map[K, Long] = self.withScope {
self.mapValues(_ => 1L).reduceByKey(_ + _).collect().toMap
}

// RDD.scala
def countByValue()(implicit ord: Ordering[T] = null): Map[T, Long] = withScope {
map(value => (value, null)).countByKey()
}

countByValue(RDD.scala)

  • 作用在普通的RDD上

  • 其实现过程调用了 countByKey

countByKey(PairRDDFunctions.scala)

  • 作用在 PairRDD 上

  • 对 key 进行计数

  • 数据要收到Driver端,结果集大时,不适用

问题:

  • countByKey可以作用在 普通的RDD上吗

  • countByValue可以作用在 PairRDD上吗

val rdd1: RDD[Int] = sc.makeRDD(1 to 10)
val rdd2: RDD[(Int, Int)] = sc.makeRDD((1 to 10).toList.zipWithIndex)

val result1 = rdd1.countByValue() //可以
val result2 = rdd1.countByKey() //语法错误

val result3 = rdd2.countByValue() //可以
val result4 = rdd2.countByKey() //可以

3.两个rdd join 什么时候有shuffle什么时候没有shuffle

其中join操作是考验所有数据库性能的一项重要指标,对于Spark来说,考验join的性能就是Shuffle,Shuffle 需要经过磁盘和网络传输,Shuffle数据越少性能越好,有时候可以尽量避免程序进行Shuffle ,那么什么情况下有Shuffle ,什么情况下没有Shuffle 呢

3.1 Broadcast join

broadcast join 比较好理解,除了自己实现外,Spark SQL 已经帮我们默认来实现了,其实就是小表分发到所有Executors,控制参数是:spark.sql.autoBroadcastJoinThreshold 默认大小是10m, 即小于这个阈值即自动使用broadcast join.

3.2 Bucket join

其实rdd方式和table类似,不同的是后者要写入Bucket表,这里主要讲rdd的方式,原理就是,当两个rdd根据相同分区方式,预先做好分区,分区结果是一致的,这样就可以进行Bucket join, 另外这种join没有预先的算子,需要在写程序时候自己来开发,对于表的这种join可以看一下 字节跳动在Spark SQL上的核心优化实践 。可以看下下面的例子

rdd1、rdd2都是Pair RDD

rdd1、rdd2的数据完全相同

一定有shuffle

rdd1 => 5个分区

rdd2 => 6个分区

rdd1 => 5个分区 => (1, 0), (2,0), || (1, 0), (2,0), || (1, 0), (2,0), || (1, 0), (2,0),(1, 0), || (2,0),(1, 0), (2,0)

rdd2 => 5个分区 => (1, 0), (2,0), || (1, 0), (2,0), || (1, 0), (2,0), || (1, 0), (2,0),(1, 0), || (2,0),(1, 0), (2,0)

一定没有shuffle

rdd1 => 5个分区 => (1,0), (1,0), (1,0), (1,0), (1,0), || (2,0), (2,0), (2,0), (2,0), (2,0), (2,0), (2,0) || 空 || 空 || 空

rdd2 => 5个分区 => (1,0), (1,0), (1,0), (1,0), (1,0), || (2,0), (2,0), (2,0), (2,0), (2,0), (2,0), (2,0) || 空 || 空 || 空

这样所有Shuffle的算子,如果数据提前做好了分区(partitionBy),很多情况下没有Shuffle.

除上面两种方式外,一般就是有Shuffle的join, 关于spark的join原理可以查看:大数据开发-Spark Join原理详解

4..transform 是不是一定不触发action

有个算子例外,那就是sortByKey,其底层有个抽样算法,水塘抽样,最后需要根据抽样的结果,进行RangePartition的,所以从job角度来说会看到两个job,除了触发action的本身算子之外,记住下面的

sortByKey → 水塘抽样→ collect

5.广播变量是怎么设计的

我们都知道,广播变量是把数据放到每个excutor上,也都知道广播变量的数据一定是从driver开始出去的,什么意思呢,如果广播表放在hive表中,那么它的存储就是在各个block块上,也对应多个excutor (不一样的叫法),首先将数据拉到driver上,然后再进行广播,广播时候不是全部广播,是根据excutor预先用到数据的,首先拿数据,然后通过bt协议进行传输,什么是bt协议呢,就是数据在分布式点对点网络上,根据网络距离来去拉对应的数据,下载者也是上传者,这样就不同每个task (excutor)都从driver上来拉数据,这样就减少了压力,另外在spark1.几的时候还是task级别,现在是共同的一个锁,整个excutor上的task共享这份数据。

关于关于Spark拷问的5个问题分别是什么就分享到这里了,希望以上内容可以对大家有一定的帮助,可以学到更多知识。如果觉得文章不错,可以把它分享出去让更多的人看到。

数据 就是 广播 内存 时候 缓冲区 排序 缓冲 作用 方式 算子 结果 抽样 问题 两个 原理 变量 性能 情况 磁盘 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 手冲咖啡和咖啡机区别 科技互联网项目 互联网与科技金融数据 科技互联网创业计划书 人人互联网科技是培训 深圳卡尔迅互联网科技有限公司怎么样 富国互联网科技创新基金 科技互联网大厂 哈尔滨屹滨互联网科技有限公司 互联网科技大奖都有哪些公司 华夏恒生科技与互联网科技 佛山市拉法互联网科技有限公司 雨阳互联网卡科技有限公司 风投北京互联网科技 互联网风格科技公司名称 互联网科技职业技能培训学校 承德科技产业互联网平台 互联网科技创业计划的风险分析 互联网企业和网络科技有限公司 前海云享互联网科技 蓝思科技飞鸽互联网 互联网金融公司科技 万易互联网科技 卓越科技互联网 招聘 新华互联网科技2019 新兴科技互联网创新大赛颁奖典礼 东莞新华互联网科技学校 北京市互联网新科技 盐城市攀科互联网科技有限公司 银川新华互联网科技学校招聘
0