大表与大表join数据倾斜_技术分享|大数据技术初探之Spark数据倾斜调优

d7dac3b4469ff316d8dea1fdb02196f6.png

侯亚南

数据技术处

cdff750f5c6d4273319131c1af44071c.png

支宸啸

数据技术处

在大数据计算中,我们可能会遇到一个很棘手的问题——数据倾斜,此时spark任务的性能会比预期要差很多:绝大多数task都很快执行完成,但个别task执行极慢或者报OOM(内存溢出)。数据倾斜调优,就是使用各种技术方案解决不同类型的数据倾斜问题,以保证Spark作业的性能。

01

#  原 理  #

数据倾斜只会发生在shuffle过程中,在进行shuffle的时候,必须将各个节点上相同的key拉取到某个节点上的一个task来进行处理,比如按照key进行聚合(groupByKey、reduceByKey、aggregateByKey)或join等操作。此时如果某个key对应的数据量特别大的话,就会发生数据倾斜,导致个别task执行极慢,整个Spark作业的运行进度是由运行时间最长的那个task决定的。

22028e08fdb873a413ebc17e7f1ac2ab.png

02

#  定位问题  #

当某个task运行过慢时,需要定位数据倾斜发生在第几个stage中。如果是用yarn-client模式提交,那么本地是直接可以看到log的,可以在log中找到当前运行到了第几个stage;如果是用yarn-cluster模式提交,则可以通过Spark Web UI来查看当前运行到了第几个stage。此外,无论是使用yarn-client模式还是yarn-cluster模式,我们都可以在Spark Web UI上深入看一下当前这个stage各个task分配的数据量,从而进一步确定是不是task分配的数据不均匀导致了数据倾斜。

22028e08fdb873a413ebc17e7f1ac2ab.png

03

#  解决方案  #

3.1  使用hive ETL进行预处理

如果hive表中的数据本身很不均匀,而且业务场景需要频繁使用Spark对hive表执行某个分析操作,此时可以尝试通过hive来进行预处理(即通过hive ETL预先对数据按照key进行聚合,或者是预先和其他表进行join),然后在Spark作业中针对的数据源是预处理后的hive表,这样在Spark作业中就不需要使用原先的shuffle类算子执行这类操作了。但这种方式属于治标不治本,只是把数据倾斜的发生提前到了hive ETL中,避免Spark程序发生数据倾斜而已。

3.2  过滤少数导致倾斜的key

如果发现导致倾斜的key就少数几个,而且对计算本身的影响并不大的话,那么可以过滤掉这些key。比如,在Spark SQL中可以使用where子句过滤掉这些key,或者在Spark Core中对RDD使用filter算子过滤掉这些key。如果需要通过动态判定哪些key的数据量最多来进行过滤,那么可以使用sample算子对RDD进行采样,然后计算出每个key的数量,取数据量最多的key过滤掉即可。该方案实现简单,而且效果也很好,可以完全规避掉数据倾斜。但大多数情况下,导致数据倾斜的key还是很多的,并不是只有少数几个。

3.3  提高shuffle操作的并行度

此方案是一种对数据倾斜迎难而上的方案,通过增加shuffle read task的数量,可以让原本分配给一个task的多个key分配给多个task,从而让每个task处理比原来更少的数据,可以通过修改spark.sql.shuffle.partitions的值来增加shuffle read task的并行度。此方案可以有效缓解数据倾斜,但是没有彻底解决问题,如果出现极端情况,比如某个key对应的数据量巨大,那么无论task数量增加到多少,这个key对应的数据还是可能会分配到一个task中去处理。

3.4  局部聚合+全局聚合

该方案适用于对RDD执行reduceByKey等聚合类shuffle算子或者在Spark SQL中使用group by语句进行分组聚合。通过将原本相同的key附加随机前缀的方式,变成多个不同的key,就可以让原本被一个task处理的数据分散到多个task上去做局部聚合,进而解决单个task处理数据量过多的问题,最后再去除掉随机前缀,进行全局聚合,就可以得到最终的结果。但如果是join类的shuffle操作,还得用其他的解决方案。

3.5  将reduce join转为map join

此方案适用于大表join小表的情况,通过不使用join算子进行连接操作,而使用Broadcast变量与map类算子来实现join操作,进而完全规避掉shuffle类的操作,彻底避免数据倾斜的发生和出现。通过将较小RDD中的数据直接用collect算子拉取到Driver端的内存中来,然后对其创建一个Broadcast变量;接着对另外一个RDD执行map类算子,在算子函数内,从Broadcast变量中获取较小RDD的全量数据,与当前RDD的每一条数据按照key进行比对。如果key相同的话,那么就将两个RDD的数据按照需要的方式连接起来。此方案不适用于两个大表join的情况。

3.6  采样倾斜key并分拆join操作

如果两个RDD/hive表进行join的时候,数据量都比较大,其中某一个RDD/hive表中的少数几个key的数据量过大,而另一个RDD/hive表中的所有key都分布比较均匀,可以将数据量大的几个key分拆成独立RDD,并附加随机前缀打散成n份去进行join。此时这几个key对应的数据就不会集中在少数几个task上,而是分散到多个task上去join了,最后将结果使用union算子合并起来即可。但如果导致倾斜的key特别多的话,不适合该方案。

3.7  使用随机前缀和扩容RDD进行join

如果在进行join操作的时候,RDD中有大量的key导致数据倾斜,可以将该RDD的每条数据都打上一个n以内的随机前缀,同时对另外一个正常的RDD进行扩容,将每条数据都扩容成n条数据,扩容出来的每条数据都依次打上一个0~n的前缀,最后将两个处理后的RDD进行join即可。该方案与上一种方案的不同之处在于,上种方案是尽量只对少数倾斜key对应的数据进行特殊处理(扩容RDD),对内存的占用并不大;而该方案是针对有大量倾斜key的情况,没法将部分key拆分出来进行单独处理,只能对整个RDD进行数据扩容,对内存资源要求很高。

实际项目中,应该综合分析数据的特征、需要进行的操作等来合理选取方案,可以多种方案组合使用。

推荐阅读

大数据技术初探之sparkstreaming与flink技术对比
技术分享|大数据技术初探之流计算框架

d2f6e95752275a578c1bff771e4c173d.gif8f8bb334a41c1ad6cd065d18427e6199.gif

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/431974.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

NYOJ 289 苹果(01背包)

苹果 时间限制:3000 ms | 内存限制:65535 KB难度:3描述ctest有n个苹果,要将它放入容量为v的背包。给出第i个苹果的大小和价钱,求出能放入背包的苹果的总价钱最大值。 输入有多组测试数据,每组测试数据第一…

磁盘剩余空间策略_MySQL磁盘消耗迅猛掌握这点就够了,包你事半功倍

Part1:写在最前当一张单表10亿数据量的表放在你面前,你将面临着什么?Part2:背景介绍为了提升数据库资源利用率,一个实例中,在不互相影响,保证业务高效的前提下,我们会将同一个大业务下的不同小业务放在一个…

Date Picker控件:

Date Picker控件: 中文:日期/时间选取器UIDatePicker有一个实例方法setDate:animated,以编程的方式选择日期。UIDatePicker有四种模式(model):Time(只选时间)Date(只选日…

logback日志pattern_@Slf4j 实现日志输入到外部文件

添加一个配置文件\src\main\resources\logback-spring.xml<?xml version"1.0" encoding"UTF-8"?><configuration scan"true" scanPeriod"10 seconds"> <contextName>logbackcontextName> <prope…

C++ Prime:sizeof运算符

sizeof运算符的结果部分地依赖于其作用的类型&#xff1a; 对char或者类型为char的表达式执行sizeof运算结果得1&#xff1b; 对引用类型执行sizeof运算得到被引用对象所占空间的大小&#xff1b; 对指针执行sizeof运算得到指针本身所占空间的大小&#xff1b; 对解引用指针执行…

前驱和后驱什么意思_为什么只有豪车才敢用后驱

为什么只有豪车才敢用后驱https://www.zhihu.com/video/1156959599864147968一般的家用车&#xff0c;基本上都是前驱为主&#xff0c;前驱够用&#xff0c;成本还低。但前驱满足不了豪华车的运动需求&#xff0c;所以豪华车后驱才是王道。有人这个时候肯定要跳出来不服了&…

leetcode 第五题 Longest Palindromic Substring (java)

Longest Palindromic Substring Given a string S, find the longest palindromic substring in S. You may assume that the maximum length of S is 1000, and there exists one unique longest palindromic substring. time255ms accepted 暴力遍历 public String longes…

思科光传输功率查询_常见的6款40G QSFP+光模块型号介绍及应用

近些年来&#xff0c;云计算和大数据在我国兴起一股热潮&#xff0c;为了提供足够的带宽&#xff0c;许多接入交换机已经发展到可以连接40G以太网的核心交换机。互连数据传输的快速发展&#xff0c;离不开40G光模块&#xff0c;因为它可以提供足够的带宽&#xff0c;以确保数据…

sigquit信号默认忽略吗_老妹儿,你真的搞懂了 Shell 信号吗?

作者&#xff1a;李振良OK链接&#xff1a;https://blog.51cto.com/lizhenliang/1899347哈喽&#xff0c;各位新来的小伙伴们&#xff0c;大家好&#xff01;由于公众号做了改版&#xff0c;为了保证公众号的资源能准时推送到你手里&#xff0c;大家记得将咱们的公众号 加星标置…

wget 命令用法详解

wget是在Linux下开发的开放源代码的软件&#xff0c;作者是Hrvoje Niksic&#xff0c;后来被移植到包括Windows在内的各个平台上。它有以下功能和特点&#xff1a; &#xff08;1&#xff09;支持断点下传功能&#xff1b;这一点&#xff0c;也是网络蚂蚁和FlashGet当年最大的卖…

datetimepicker不可以选择当天之前_专访吴京:网上《战狼3》的消息我都不知道,大家可以选择不信...

搜狐娱乐讯 (哈麦/文)在2017爆火的《战狼2》之后&#xff0c;吴京演了《祖宗十九代》《流浪地球》《老师好》《银河补习班》《攀登者》《我和我的祖国》《我和我的家乡》《金刚川》八部电影&#xff0c;但是计划中的《战狼3》一直没有动静。不过&#xff0c;关于《战狼3》&…

机器人蛮王_盖伦:吊打我老婆,蛮王:我也是,他:被老婆打的不敢出塔

相遇就是缘分&#xff0c;你点开了我的文章&#xff0c;小编感到万分荣幸&#xff0c;感谢各位朋友。既然看到了我的文章&#xff0c;就说明我们还是有缘&#xff0c;希望大家可以帮我点点左上角的蓝色字体&#xff0c;小编给大家鞠躬了&#xff01;LOL如此好玩的原因&#xff…

栈 详解

官方定义是这样的&#xff1a;栈&#xff08;Stack&#xff09;是一个后进先出的线性表&#xff0c;它要求只在表尾进行删除和插入操作。 栈是一种重要的线性结构&#xff0c;可以这样讲&#xff0c;栈是线性表的一种具体表现形式&#xff0c;但是它在操作上有一些特殊的要求和…

android serialport new 软件退出_基于Android9.0,了解Android启动流程

先记住四个进程和三种方式。**四个进程**1.Launcher进程2.system_server进程3.App进程4.Zygote进程**三种方式**1.Binder方式2.Socket方式3.Handler方式点击桌面APP图标&#xff0c;Launcher调用startActivitySafely&#xff08;Launcher进程&#xff09;java/*** Default laun…

Objective-C 学习笔记

超类 即父类&#xff0c;通过 [super setName: "a"] 可以调用超类方法 复合 是指一个对象由其他多个对象组成 对象初始化 interface Car : NSObject (Engine *engine; ) endimplementation Car - (id) init {  //因init方法可能返回不同的对象&#xff0c;所以需要…

【转】使用命令行方式创建和启动android模拟器

原文网址&#xff1a;http://blog.csdn.net/tiandinilv/article/details/8953001 1、Android模拟器介绍 Android中提供了一个模拟器来模拟ARM核的移动设备。Android的模拟器是基于QEMU开发的&#xff0c;QEMU是一个有名的开源虚拟机项目&#xff08;详见http://bellard.org/qem…

centos7限制cpu使用_Linux系统进程CPU使用率限制脚本

一、背景近日在客户系统运维中发现&#xff0c;有系统在定时脚本执行期间会将Linux系统CPU利用率跑满&#xff0c;导致其他服务受到影响&#xff0c;故查阅资料发现有大神写的CPU利用率限制程序。地址&#xff1a;CPU Usage Limiter for Linux根据此编写脚本&#xff0c;配合定…

LPC1768的SPI通讯

SPI是一种全双工串行接口&#xff0c;可处理多个连接到指定总线上的主机和从机。在数据传输过程中总线上只能有一个主机和一个从机通信。在数据传输中&#xff0c;主机总是会向从机发送一帧8到16个位的数据&#xff0c;而从机也总会向主机发送一帧字节数据 使用代码如下 void S…

python 项目实战视频_腾讯视频 Python 爬虫项目实战

做了一些小项目&#xff0c;用的技术和技巧会比较散比较杂&#xff0c;写一个小品文记录一下&#xff0c;帮助熟悉。需求&#xff1a;经常在腾讯视频上看电影&#xff0c;在影片库里有一个"豆瓣好评"板块。我一般会在这个条目下面挑电影。但是电影很多&#xff0c;又…

Java中文乱码问题(转)

解决JSP中文乱码问题 大家在JSP的开发过程中&#xff0c;经常出现中文乱码的问题&#xff0c;可能一至困扰着大家&#xff0c;现把JSP开发中遇到的中文乱码的问题及解决办法写出来供大家参考。首先了解一下Java中文问题的由来&#xff1a; Java的内核和class文件是基于unicode的…