在SQL开发过程中,可能会遇到将一个数组字段的所有元素拆分到原始行的数据分析场景(如下图),本文将罗列在ClickHouse和Doris中如何进行SQL编写实现该逻辑。
文章导航
ClickHouse
在ClickHouse中,ARRAY JOIN子句是一种强大的功能,它允许开发者将包含数组列的表转换为一个新表,其中包含了原始数组中的每个单独元素。这种操作类似于执行JOIN操作,但是是在单个表的内部进行,适用于行转列的场景。
操作步骤:
- 新建含有数组元素的数据表
CREATE TABLE hobby
(
name String,
hobby Array(UInt8)
) ENGINE = Memory;
- 执行插入逻辑
INSERT INTO hobby
VALUES ('a', [1,2]), ('b', [3,4,5]), ('c', []);
- 使用ARRAY JOIN 进行查询
SELECT name, hobby
FROM hobby
ARRAY JOIN arr;
Doris
Doris 中的炸裂函数是一种用户自定义表生成函数。它的主要作用是将一行输入数据转换为多行输出数据,就像是把一个 “包裹”拆开,将里面的每个元素分别作为新的行进行输出。例如,当一个列中存储了一组值(如数组),而我们希望对数组中的每个元素进行单独的处理或关联操作时,就可以使用炸裂函数来将数组元素展开成多行,方便后续的查询和分析。
操作步骤:
- 新建含有数组元素的数据表
CREATE TABLE user_hobbies (
user_id INT,
hobbies ARRAY<VARCHAR>);
- 执行插入逻辑
INSERT INTO user_hobbies VALUES(1, ['reading', 'writing']),(2, ['sports', 'music', 'travel']);
- 使用LATERAL VIEW EXPLODE(数组元素)
SELECT user_id, exploded_hobby
FROM user_hobbies
LATERAL VIEW EXPLODE(hobbies) exploded_table AS exploded_hobby;
两者差异
CK 中的array join与 Doris 中的LATERAL VIEW EXPLODE功能相似,都可展开数组数据为单独行并保持与原始表其他列关联。
- 语法上,array join简洁,直接在FROM子句后使用;LATERAL VIEW EXPLODE相对复杂,需二者配合使用。
- 性能方面,都受数据分布及查询情况影响,CK 的在数据存储合理、查询简单时高效,复杂关联时性能或下降。Doris 能利用 MPP 架构并行处理,但数据分布不均等情况会影响性能。
- 适用场景上,CK 适用于高性能、简单直接查询及本地存储数据分析场景;Doris 更适合分布式复杂数据结构处理及多表关联、复杂转换的场景。