spark 数据倾斜优化总结

2023-09-17 23:15:16

一、数据倾斜产生原因

数据倾斜就是部分task承担了过多的计算任务,导致整个stage都被卡。
可能产生数据倾斜的场景如下

操作场景
join其中一个表比较小,但key值少
join大表与大表,但key值中存在过多的特殊值,如0或null
joinon条件包含key值过滤逻辑,导致部分数据被保留,部分被过滤,最终节点分布不均
join多对多关系表join导致数据膨胀
group by某个组合数量特别多
count distinct需要集中最后一个reduce节点处理,特殊值多就会慢
使用脚本或udf会存在强制数据分布在少量节点的可能
distriute by存在值不均匀的可能
读取上游文件数过少,单个文件过大

二、数据倾斜优化

2.1 调参优化

参数作用备注
hive.map.aggr=truemap端部分聚合仅适用于hive引擎,不适用于spark。spark本身就支持map端的局部聚合
hive.groupby.skewindata=true参数设置为true时,生成的查询计划会有2个MR job。第一个MR中,map的输出结果会随机分配到reduce中,每个reduce做部分聚合操作,并输出结果,这样相同的key会被分发到不同的reduce中,起到了负载均衡的目的,第二个MR再根据第一个MR预处理的结果,完成聚合操作仅适用于hive引擎,spark不支持此参数

2.2 代码优化

2.2.1 join类操作
  1. 如果是join操作,那么采用join key分布最均匀的表作为驱动表
  2. where类的操作在join前进行
2.2.1.1 小表join大表

使用 /*+mapjoin(a)*/ 让小的维度表先进内存,在map端完成reduce
使用此操作需要对小的维度表配置DQC数据量监控,以避免进入内存的维表数据过大

2.2.1.2 中表join大表

在维表大小中等,完全进入内存可能报错;但日志与维表关联部分出现某种行为的维值较少时,可以采用两次 mapjoin 的方式优化倾斜问题。例,有交易日志log,和维表dim,它们2次join示例如下

select /*+mapjoin(b)*/
    a.*, 
    b.*
from log a
left join (
    select /*+mapjoin(d)*/
           c.*
      from dim AS c
            join (
                select dim_id
                 from log
                group by dim_id
            ) AS d 
            on c.dim_id = d.dim_id
    ) AS b 
 on a.dim_id = b.dim_id
2.2.1.3 大表join大表

大表join大表一般由于key值存在 null 等特殊值,导致数据过于集中倾斜。这种情况可以使用hash函数将key打散。这里不要用rand,因为fetch failed后,整个job会被kill

2.2.1.4 join条件包含key值过滤逻辑

尽量在join前使用where过滤

2.2.1.5 多对多关系表join
  1. 去掉热点大key
  2. 增加关联条件
  3. 减少数据范围,笛卡尔积结果尽量控制1亿
2.2.2 group by操作

将倾斜数据拿出来单独处理,后面再union 回去

2.2.3 count distinct操作
2.2.3.1 单个 count distinct

可以将它转换为count+group by。如果单个值数据量比较集中,可以过滤该值,结果+1.
下面的示例是从t表中取user_id的uv。其中,user_id有大量为0的异常值
优化前

select count(distinct user_id) as uv from t

优化后

select count(user_id) +1 as uv
   from (
   	select user_id
   	  from t
   	 where user_id != 0
   	 group by user_id
)
2.2.3.1 多个 count distinct

如果多个count distinct,去重的键是一样的,如对用户计算uv和去作弊uv,那么仍可按user_id去重后,根据是否作弊按0,1进行SUM。
如果去重的键是不一样的,那么多个count distinct 可以优化为多个group by再union all的方式。但这会扫描多次表,具体优化效果需根据具体情况测试确定。

2.2.4 使用脚本或udf

这个需要根据具体业务场景优化。如果不方便优化,可以降低 spark.sql.shuffle.partitions的值。

2.2.5 distriute by

distriute by 需要保证键比较均匀。同时,不能使用rand函数,否则shuffle fetch failed后,整个job会被kill

2.2.6 读取操作

读取一般不会倾斜。出现倾斜一般是上游文件数过少,下游处理的executor多。spark默认一个executor对应一个文件,这样会有大量executor空跑。这种情况可以使用 distriute by、repartition 等对文件重新分区。

更多推荐

“混合”引擎为通用子模块提供动力,实现嵌入式I / O灵活性

现成的组件对于嵌入式开发工程师而言并不是什么新鲜事物。但是,实际上没有人期望一种“一刀切”的解决方案,尤其是在涉及复杂的I/O要求的情况下。但是,基于流行的夹层卡格式的具有成本效益的现场可编程门阵列(FPGA)技术的新实现正在“针对VME,PCI,CompactPCI和VME提供可承受的标准硬件和自由形式的I/O多功能

Mac FoneLab for Mac:轻松恢复iOS数据,专业工具助力生活

如果你曾经不小心删除了重要的iOS数据,或者因为各种原因丢失了这些数据,那么你一定知道这种痛苦。现在,有一个名为MacFoneLab的Mac应用程序,它专门设计用于恢复iOS数据,这可能是你的救星。MacFoneLabforMac是一种强大的工具,它可以帮助你恢复各种类型的iOS数据,包括照片、视频、联系人、短信、通话

Vulnhub实战-DC9

前言本次的实验靶场是Vulnhub上面的DC-9,其中的渗透测试过程比较多,最终的目的是要找到其中的flag。一、信息收集对目标网络进行扫描arp-scan-l对目标进行端口扫描nmap-sC-sV-oAdc-9192.168.1.131扫描出目标开放了22和80两个端口,访问目标的80端口。对目标进行目录扫描与分析。

大数据课程M2——ELK的ELASTICSEARCH概述

文章作者邮箱:yugongshiye@sina.cn地址:广东惠州▲本章节目的⚪了解ELK的ELASTICSEARCH概括;⚪掌握ELK的ELASTICSEARCH核心概念;一、ELASTICSEARCH概括1.ES安装和启动注意:如果使用达内云主机,无需安装es,直接配置yml启动即可。1.安装下载ES最新版本的安装

iOS xcframework项目提示“ld: framework not found”

iOSxcframework项目提示“ld:frameworknotfound”问题描述公司有一个项目,同时引用了.framework和.xcframework,但是使用xcode编译的时候,xcodebuildarchive-project${project_Name}.xcodeproj-target${targe

FreeRTOS移植以及核心功能

文章目录freertos和ucos区别,优缺点比较移植步骤核心功能内存管理(5种内存管理策略)FreeRTOS任务调度算法有三种时间管理通信管理栈管理freertos和ucos区别,优缺点比较FreeRTOS(FreeReal-TimeOperatingSystem)和uC/OS(Micro-controllerOpe

使用Leaflet对WMS做空间几何范围查询

一、需求使用GeoServer发布的WMS服务对WMS做空间范围查询,默认情况下WMS支持点击查询,网上有很多的资料不在赘述。那么WMS做几何查询该怎么实现呢?二、实现路径查询WMS查询的服务参数,WMS支持三种请求方式:GetCapabilities、GetMap、GetFeatureInfo。其中GetCapabi

Transaction - 记一次 Spring 事务联合 Redis 挂了引发的生产事故

问题描述java.lang.RuntimeException:java.lang.IllegalStateException:Alreadyvalue[…数据源信息…]boundtothread[[Ljava.lang.String;@231b1ae0.container-0-C-1]上述问题是本次问题的最终结果,但并

springboot和vue:二、springboot特点介绍+热部署热更新

springboot特点介绍能够使用内嵌的Tomcat、Jetty服务器,不需要部署war文件。提供定制化的启动器Starters,简化Maven配置,开箱即用。纯Java配置,没有代码生成,也不需要XML配置。提供了生产级的服务监控方案,如安全监控、应用监控、健康检测等。热部署热更新SpringBoot提供了spri

SSD上 NVIDIA Jetson Orin NANO系統如何刷

对于AI计算性能高达40TOPS的JetsonOrinNano开发套件来说,如果缺少性能够好的存储相匹配,会让总体执行效益大打折扣。为此,NVIDIA在JetsonOrinNano开发套件上配置2个M.2接口(如下图),最高能安装2片高速PCIe总线的NVMe高速存储设备,这样大大提升了这个产品的实用性。由于M.2设备

Java中常见的线程池

一、Java中常见的线程池1.为什么使用线程池重用线程池的线程,避免因为线程的创造和销毁所带来的性能开销。有效控制线程池的最大并发数,避免大量的线程之间因抢占系统资源而阻塞。能够对线程进行简单的管理,并提供一些特定的操作,如:定时、定期、单线程、并发数控制等功能。2.线程池可能带来的风险死锁任何多线程应用程序都有死锁风

热文推荐