hadoop - 在大型 (50 GB) 数据集上没有 Partition BY 子句的 Hive 窗口函数 ROW_NUMBER 非常慢。有没有更好的优化方法?
问题描述
我有一个包含 5000 万条记录的 HDFS 文件,原始文件大小为 50 GB。
我正在尝试将其加载到配置单元表中,并在加载时使用以下内容为所有行创建唯一 ID。我正在使用 Hive 1.1.0-cdh5.16.1。
row_number() over(order by event_id, user_id, timestamp) as id
在执行时,我看到在 reduce 步骤中,分配了 40 个 reducer。39 个 reducer 的平均时间约为 2 分钟,而最后一个 reducer 大约需要 25 分钟,这显然让我相信大部分数据都是在一个 reducer 中处理的。
我怀疑 Order By 条款是这种行为的原因,并尝试了以下方法,
row_number() over() 作为 id
然而,我看到了同样的行为。
考虑 Map Reduce 范式,我觉得如果我们不指定 Partition BY 子句,数据必须在一个 reducer(非分布式)中处理,以便查看所有行并附加正确的行号。对于没有 partition By 子句或 partition By 偏斜列的任何 Window 函数,这可能是正确的。
现在,我的问题是,当我们不得不避免 Partition BY 子句时,我们如何规避这个问题并优化窗口功能?
解决方案
您可以使用 UUID:
select java_method('java.util.UUID','randomUUID')
在您的系统/工作流程中生成的 UUID 在其他系统中也将是唯一的,因为 UUID 是全局唯一的。UUID 完全分布式且快速运行。
同样在 Hive 3.x 中,您可以在 DDL 中使用SURROGATE_KEY函数
推荐阅读
- rabbitmq - 在 RabbitMQ 中检测到网络分区
- flutter - 颤振:storekit_duplicate_product_object。有相同产品标识符的待处理交易
- google-cloud-platform - 在同一项目中使用 Cloud Composer 和 Cloud Functions 时,如何使用 VPC Service Controls 在 GCP 上配置防火墙规则和 DNS 设置?
- c++ - 如何测试使用 Boost.MPI 和 Boost.Test 的程序?
- sql - SQL JSON_TABLE 查询需要两个表来运行查询
- python - 如何将形状为 (4498,) 的张量转换为 (None, 4498)?
- python - 有什么办法可以让我获得 wagtail 管理屏幕的 html 吗?
- amazon-web-services - AWS Terraform - 在资源上使用动态块
- reactjs - 如何在 React AgGrid 表中动态启用编辑模式
- c++ - 将 R 代码转换为 C++ 以实现 Rcpp