混合直方图综合了频率直方图和高度均衡直方图的一些特征。创建混合直方图与创建高度均衡直方图都是以同样的方法开始的。随后进行了以下两项重要的改进。
Ø 每个不重复值都关联到一个单独的桶(换句话说,为高度均衡直方图定义的常见值的概念不复存在)。基于该目的,桶的限制被转移了。结果,每个桶可能会根据不同数量的记录来创建。
Ø 频率被加入到每个桶的端点值中。因此,对于端点值,而且仅对于端点值而言,就有了某种频率直方图可用。
测试表有两个混合直方图。例如,我们看一下为val1列(注意,该列拥有22个不同的值)创建的那个混合直方图。下面查询的输出显示了该混合直方图包含的数据集:
COLUMN percent FORMAT 90.9
SELECT val1, count(*),
ratio_to_report(count(*)) OVER ()*100 AS percent
FROM t
GROUP BY val1
ORDER BY val1;
P198
如果数据库引擎被要求创建有10个桶的直方图,那么不管是频率直方图还是高频率直方图,都无法应用。前者不适用是因为桶的数量小于不重复值的数量,后者是因为top-10的值仅代表约80%的记录(根据公式8-1需要代表90%的值;90=100-100/10)。因此,就有了提供以下信息的混合直方图:
SELECT endpoint_value, endpoint_number,
endpoint_number - lag(endpoint_number,1,0)
OVER (ORDER BY
endpoint_number) AS count,
endpoint_repeat_count
FROM user_tab_histograms
WHERE table_name = 'T'
AND column_name = 'VAL1'
ORDER BY endpoint_number;
P199
请注意,在上面的输出中,一方面,endpoint_number列提供关于每个桶上关联的记录数量的信息,而另一方面,endpoint_repeat_count列提供端点值的频率信息。根据这个信息,由查询优化器执行的关于端点值的估算就可以做到精确。下面是一个例子:
DELETE plan_table;
EXPLAIN PLAN SET STATEMENT_ID '44' FOR
SELECT * FROM t WHERE val1 = 44;
EXPLAIN PLAN SET STATEMENT_ID '50' FOR
SELECT * FROM t WHERE val1 = 50;
EXPLAIN PLAN SET STATEMENT_ID '56' FOR
SELECT * FROM t WHERE val1 = 56;
COLUMN statement_id FORMAT A12
SELECT statement_id, cardinality
FROM plan_table
WHERE id = 0
ORDER BY statement_id;
STATEMENT_ID CARDINALITY
44 26
50 102
56 30
提示 混合直方图提供的信息要比高度均衡直方图提供的信息好得多。基于这个原因,从12.1版本开始,就可以并且也应该完全忽略掉高度均衡直方图了。
1.1.1.1 无直方图
请注意,user_tab_histograms视图为每个没有直方图的列显示了两行数据,这非常有意义。这是因为最小值和最大值分别存储在端点号0和1上。举例来说,对于id列的内容,没有直方图可用,就会显示为下面的样子:
SELECT endpoint_value, endpoint_number
FROM user_tab_histograms
WHERE table_name = 'T'
AND column_name = 'ID';
ENDPOINT VALUE ENDPOINT_NUMBER
1 0
1000 1




