【 使用环境 】测试环境
【 OB or 其他组件 】
【 使用版本 】5.7.25-OceanBase_CE-v4.3.0.1
【问题描述】
如下图所示,select distinct dw_table_name from dw_task_row_id t where t.dw_table_name like ‘SP_UPDATE_COMPLEMENT_GID%’;
查询dw_task_row_id表中dw_table_name字段存在四个以“SP_UPDATE_COMPLEMENT_GID”开头的结果
select dw_table_name,count(1) from dw_task_row_id t where t.dw_table_name like ‘SP_UPDATE_COMPLEMENT_GID%’ group by dw_table_name;
换成group by dw_table_name字段查询时,出现的结果如下,dw_table_name分组后出现两组重复,并且缺少一组数据
根据您提供的信息,SELECT DISTINCT 和 GROUP BY 的查询结果不一致,这确实看起来有些异常。通常情况下,SELECT DISTINCT 应该返回与 GROUP BY 相同的结果集,因为它们都是为了去重。
分析与建议
检查数据一致性:
请确保数据在查询时没有发生变化。可以先锁定表,然后再次运行这两个查询,看看结果是否一致。
您可以尝试在一个事务中执行这两个查询,以确保数据的一致性。
检查执行计划:
使用 EXPLAIN 查看两个查询的执行计划,看看是否有不同的优化策略导致了结果的差异。
例如,EXPLAIN SELECT DISTINCT dw_table_name FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' 和 EXPLAIN SELECT dw_table_name, COUNT(1) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' GROUP BY dw_table_name。
检查索引:
确认 dw_table_name 列上有合适的索引。索引的存在可能会影响查询的执行计划。
您可以使用 SHOW INDEX FROM dw_task_row_id 查看索引信息。
检查数据内容:
检查 dw_table_name 列的数据内容,特别是是否有不可见字符或空格导致的差异。
例如,可以使用 SELECT HEX(dw_table_name) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' 查看数据的十六进制表示。
使用 Hint 强制优化器行为:
尝试使用 Hint 强制优化器使用特定的算法。例如,使用 /*+ USE_HASH_AGGREGATION */ 或 /*+ NO_USE_HASH_AGGREGATION */。
例如:
EXPLAIN SELECT /*+ USE_HASH_AGGREGATION */ DISTINCT dw_table_name FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%';
EXPLAIN SELECT /*+ USE_HASH_AGGREGATION */ dw_table_name, COUNT(1) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' GROUP BY dw_table_name;
示例
检查数据一致性:
START TRANSACTION;
SELECT DISTINCT dw_table_name FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%';
SELECT dw_table_name, COUNT(1) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' GROUP BY dw_table_name;
COMMIT;
检查执行计划:
EXPLAIN SELECT DISTINCT dw_table_name FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%';
EXPLAIN SELECT dw_table_name, COUNT(1) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' GROUP BY dw_table_name;
检查索引:
SHOW INDEX FROM dw_task_row_id;
检查数据内容:
SELECT HEX(dw_table_name) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%';
使用 Hint:
EXPLAIN SELECT /*+ USE_HASH_AGGREGATION */ DISTINCT dw_table_name FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%';
EXPLAIN SELECT /*+ USE_HASH_AGGREGATION */ dw_table_name, COUNT(1) FROM dw_task_row_id t WHERE t.dw_table_name LIKE 'SP_UPDATE_COMPLEMENT_GID%' GROUP BY dw_table_name;