doris处理多个审批人

select tb1.apply_Id,
                   group_concat( cast( tb2.user_id as string ) ) new_current_userId,
                   group_concat( tb2.staff_name )                new_current_username
              from ( select apply_id, userid from dwd.dwd_idmp_hr_sys_apply_info_di lateral view explode_split(split_part(current_userId, ':', 2), ',') tmp1 as userid ) tb1
                   left join ( select * from dim.dim_idmp_hr_staff_info_dd where date_value = 20230403 ) tb2
                             on tb1.userid = tb2.user_id
             group by tb1.apply_Id 
要处理的数据类型:

 处理后的结果:

 

<think>我们被要求回答关于Doris中多字段DISTINCT的使用方法。在Doris中,如果我们想要对多个字段进行去重,有几种方法可以实现。下面我将结合站内引用和Doris的特性来回答。 根据引用[1]中提到的,在SQL中如果要对多个字段进行去重,可以使用子查询结合GROUP BY的方式,即先通过GROUP BY对多个字段分组,然后取每组中的一条记录(比如使用MIN或MAX函数取主键)。这种方法同样适用于Doris。 另外,Doris本身也支持使用DISTINCT关键字对多个字段进行去重,但是需要注意的是,DISTINCT在Doris中用于SELECT后面时,会对后面所有列的组合进行去重。此外,Doris还提供了Bitmap和HLL(HyperLogLog)等近似去重的方法,适用于大数据量下的去重统计。 下面我们详细说明: 方法一:使用DISTINCT关键字 直接在SELECT后使用DISTINCT,后面跟上多个字段,表示根据这些字段的组合进行去重。 示例: ```sql SELECT DISTINCT field1, field2, field3 FROM table_name; ``` 方法二:使用GROUP BY 使用GROUP BY对多个字段分组,然后选择需要的字段。这种方法可以结合聚合函数来获取其他列的值。 示例: ```sql SELECT field1, field2, field3 FROM table_name GROUP BY field1, field2, field3; ``` 方法三:使用子查询(当需要保留重复记录中的某一条时) 如果我们不仅要去重,还要在重复记录中保留一条(比如保留id最小的那一条),可以使用引用[1]中的方法: ```sql SELECT field1, field2, field3 FROM table_name WHERE id IN (SELECT MIN(id) FROM table_name GROUP BY field1, field2, field3); ``` 这里假设表中有主键id,我们通过子查询先按多个字段分组,然后取每组的最小id,最后通过IN来获取这些id对应的记录。 方法四:近似去重(适用于大数据量) 如果不需要精确去重,而只是需要统计去重后的数量,可以使用Doris提供的Bitmap或HLL函数。 例如,使用HLL_UNION_AGG和HLL_HASH进行多字段的近似去重计数: ```sql SELECT HLL_UNION_AGG(HLL_HASH(CONCAT(field1, field2, field3))) FROM table_name; ``` 注意:这里将多个字段拼接成一个字符串,然后使用HLL_HASH计算哈希值,再通过HLL_UNION_AGG聚合得到近似的去重计数。 方法五:使用窗口函数(Doris支持窗口函数) 我们可以使用ROW_NUMBER()窗口函数来对分组内的记录进行编号,然后取第一行。 示例: ```sql SELECT * FROM ( SELECT field1, field2, field3, ROW_NUMBER() OVER (PARTITION BY field1, field2, field3 ORDER BY id) as row_num FROM table_name ) t WHERE row_num = 1; ``` 这里按照多个字段分组,然后按id排序(或其他排序字段),每组取第一条。 下面我们通过一个具体示例来展示: 假设有一个订单表(orders),包含以下字段:order_id(订单ID)、customer_id(客户ID)、product_id(产品ID)、order_date(订单日期)。我们想要获取每个客户每个产品的第一个订单(即每个客户每个产品组合去重,保留最早订单)。 方法一:使用DISTINCT(但这样只能得到客户和产品的组合,无法得到订单日期) ```sql SELECT DISTINCT customer_id, product_id FROM orders; ``` 方法二:使用GROUP BY(同样,无法直接得到订单日期,除非使用聚合函数) 如果我们想得到每个客户每个产品的最小订单日期,可以: ```sql SELECT customer_id, product_id, MIN(order_date) AS first_order_date FROM orders GROUP BY customer_id, product_id; ``` 方法三:使用子查询(保留完整记录) ```sql SELECT * FROM orders WHERE order_id IN ( SELECT MIN(order_id) FROM orders GROUP BY customer_id, product_id ); ``` 这里假设order_id是主键,并且我们取最小order_id对应的记录(即最早订单)。 方法五:使用窗口函数 ```sql SELECT * FROM ( SELECT order_id, customer_id, product_id, order_date, ROW_NUMBER() OVER (PARTITION BY customer_id, product_id ORDER BY order_date) as rn FROM orders ) t WHERE rn = 1; ``` 总结: 在Doris中实现多字段去重,根据需求选择合适的方法: 1. 只需要去重后的字段组合:使用DISTINCT或GROUP BY。 2. 需要保留重复记录中的一条(并获取其他字段的值):使用子查询(结合MIN/MAX)或窗口函数。 3. 只需要去重计数(且数据量很大,允许近似):使用HLL函数。 4. 需要精确去重计数:使用COUNT(DISTINCT ...) 但是注意,Doris的COUNT(DISTINCT)在多个字段时,需要将多个字段拼接成一个字符串(或者使用多个字段)或者使用GROUP BY来计数,例如: ```sql SELECT COUNT(*) FROM (SELECT customer_id, product_id FROM orders GROUP BY customer_id, product_id) t; ``` 注意:在Doris中,COUNT(DISTINCT)对多个字段的支持在早期版本中可能有限,通常的做法是使用GROUP BY子查询。但是,在Doris 1.2版本之后,已经支持多列的COUNT(DISTINCT),例如: ```sql SELECT COUNT(DISTINCT customer_id, product_id) FROM orders; ``` 但是,请注意,这种写法在Doris中是否支持取决于版本。在较新的版本(如1.2+)中支持,但若版本较低,则可能不支持。因此,如果遇到不支持的情况,可以使用子查询。 最后,根据引用[2]提到的物化视图,如果去重查询是高频且数据量大的,可以考虑创建物化视图来加速查询。 相关问题: 1. Doris中如何对多个字段进行COUNT(DISTINCT)操作? 2. Doris中如何创建物化视图来优化去重查询? 3. 如何用HLL函数实现多字段的近似去重计数? 以上,我们详细介绍了Doris中多字段去重的各种方法,用户可以根据自己的需求选择合适的方法。</think>在 Doris 中实现多字段的 `DISTINCT` 操作,主要有以下几种方法(结合引用内容优化): ### 一、基础方法:`GROUP BY` 多字段分组 ```sql SELECT field1, field2, field3 FROM your_table GROUP BY field1, field2, field3; ``` **原理**:通过多字段分组实现去重,类似引用[1]中的 `GROUP BY` 方案[^1]。 --- ### 二、精确去重方案 #### 1. 使用 `DISTINCT` 关键字(推荐) ```sql -- 多字段组合去重 SELECT DISTINCT field1, field2, field3 FROM your_table; -- 带聚合计算的去重 SELECT AVG(DISTINCT salary) AS avg_salary, COUNT(DISTINCT CONCAT(department, '-', position)) AS unique_positions FROM employees; ``` #### 2. 子查询 + `MIN/MAX`(保留特定记录) ```sql SELECT * FROM your_table WHERE id IN ( SELECT MIN(id) -- 或 MAX(id) 保留最后一条 FROM your_table GROUP BY field1, field2, field3 -- 按需组合字段 ); ``` **适用场景**:需要保留重复组中的第一条或最后一条记录(引用[1]方法)[^1]。 --- ### 三、高性能近似去重(大数据量优化) #### 1. Bitmap 精确去重 ```sql SELECT BITMAP_UNION_COUNT(bitmap_hash(field1, field2)) AS distinct_count FROM your_table; ``` **优势**:TB级数据毫秒响应,需在建表时预聚合。 #### 2. HLL 近似去重(误差<1%) ```sql SELECT HLL_UNION_AGG(HLL_HASH(CONCAT(field1, field2))) AS approx_distinct FROM your_table; ``` --- ### 四、物化视图优化(引用[2]) 对高频查询创建预聚合物化视图[^2]: ```sql CREATE MATERIALIZED VIEW mv_distinct_fields BUILD IMMEDIATE REFRESH AUTO AS SELECT field1, field2, field3, BITMAP_UNION(bitmap_hash(field1, field2, field3)) AS distinct_bitmap FROM your_table GROUP BY field1, field2, field3; ``` **查询时直接使用**:`SELECT COUNT(DISTINCT *) FROM mv_distinct_fields` --- ### 五、跨周统计示例(结合引用[3]) ```sql SELECT DATE_FORMAT(event_time, '%Y%u') AS week_key, COUNT(DISTINCT user_id, device_id) AS unique_devices -- 多字段去重 FROM user_events WHERE event_date BETWEEN '2023-01-01' AND '2023-12-31' GROUP BY week_key; ``` **说明**: 1. `%Y%u` 实现年周格式化(引用[3]方法)[^3] 2. `COUNT(DISTINCT col1, col2)` 直接多字段去重计数 --- ### 六、性能对比 | 方法 | 精确性 | 适用数据量 | 响应速度 | 存储开销 | |--------------------|--------|------------|----------|----------| | `GROUP BY` 分组 | 精确 | 百万级 | 中等 | 低 | | Bitmap | 精确 | 十亿级 | 毫秒级 | 中等 | | HLL | 近似 | 百亿级 | 毫秒级 | 极低 | | 物化视图 | 精确 | 任意 | 亚秒级 | 较高 | > **最佳实践**: > - 千万级以下:直接用 `DISTINCT` 或 `GROUP BY` > - 亿级以上:优先用 Bitmap/HLL > - 高频查询:通过物化视图预计算[^2]
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值