Исключение представлений
Рассмотрим запрос Q8, являющийся упрощенным вариантом запроса 18 тестового набора TPC-H.
Q8
SELECT o_orderkey, c_custkey, SUM(l_quantity) FROM orders, lineitem L1, customers WHERE o_orderkey = l_orderkey AND c_custkey = o_custkey AND o_orderkey IN (SELECT l_orderkey FROM lineitem L2 GROUP BY l_orderkey HAVING SUM(l_quantity) > 30) GROUP BY o_orderkey, c_custkey;
Подзапрос Q8 подвергается преобразованию устранения вложенности, что приводит к порождению запроса Q9. К встроенному представлению (производной таблице) V2, появившемуся в в Q9 из-за устранения вложенности, не требуется применять полусоединение, так как здесь имеется эквисоединение, и столбцы соединения V2 обладают свойством уникальности, поскольку являются единственными столбцами группировки в V2.
Q9
SELECT o_orderkey, c_custkey, SUM(l_quantity) FROM orders, lineitem L1, customers, (SELECT l_orderkey FROM lineitem L2 GROUP BY l_orderkey HAVING SUM(l_quantity) > 30) V2 WHERE o_orderkey = V2.l_orderkey AND o_orderkey = L1.l_orderkey AND c_custkey = o_custkey GROUP BY o_orderkey, c_custkey;
Как показывает запрос Q10, с использованием перестановки группировки и соединения (т.е. размещения группировки, group-by placement) [5], [6], [8] можно получить еще одно представление V1, содержащее таблицу L1; в список выборки раздела SELECT представления V2 добавляется SUM(l_quantity), что не изменяет семантику Q9.
Q10
SELECT o_orderkey, c_custkey, SUM(V1.qty) FROM orders, customers, (SELECT l_orderkey, SUM(l_quantity) qty FROM lineitem L2 GROUP BY l_orderkey HAVING SUM(l_quantity) > 30) V2, (SELECT l_orderkey, SUM(l_quantity) qty FROM lineitem L1 GROUP BY l_orderkey) V1 WHERE o_orderkey = V2.l_orderkey AND o_orderkey = V1.l_orderkey AND c_custkey = o_custkey GROUP BY o_orderkey, c_custkey;
Как можно видеть, V1 и V2 — это разные экземпляры одного и того же представления, за исключением того, что предикаты фильтрации в V2 являются более ограничительными, чем в V1, из-за наличия в V2 раздела HAVING. Кроме того, эквисоединения V1 и V2 с таблицей orders производятся по столбцу o_orderkey, обладающему свойством уникальности, так как это единственный столбец группировки в этих представлениях; таким образом, эти два соединения являются фильтрующими соединениями. Следовательно, представление V1 можно исключить, а ссылки на V1 можно заменить ссылками на V2. Исключение фильтрующего представления из Q10 приводит к запросу Q11.
Q11
SELECT o_orderkey, c_custkey, SUM(V2.qty) FROM orders, customers, (SELECT o_orderkey, SUM(l_quantity) FROM lineitem GROUP BY l_orderkey HAVING SUM(l_quantity) > 30) V2 WHERE o_orderkey = V2.l_orderkey AND c_custkey = o_custkey GROUP BY o_orderkey, c_custkey;
Если бы представление V2 в запросе Q9 подвергалось слиянию, то могла бы быть приведена другая аргументация использования фильтрующего соединения с тем же результатом исключения таблицы lineitem
из внешнего запроса.
Если известно, что amount_sold положительно; например, в случае ограничения целостности базы данных типа RELY