为视图引用的底层表创建合适的索引是提升视图查询性能的基础。需根据查询模式选择索引类型:
WHERE column = value)、范围查询(如WHERE column BETWEEN value1 AND value2)和前缀匹配查询(如WHERE column LIKE 'prefix%'),是Oracle默认的通用索引类型。(column1, column2)),需将高频过滤列或连接列放在前面(如视图查询中常用department_id过滤,则索引应为(department_id, employee_id))。UPPER(name)、TO_CHAR(create_date, 'YYYY-MM')),可创建函数索引(如CREATE INDEX idx_upper_name ON employees(UPPER(name))),使基于函数的查询能利用索引。对于频繁访问、计算逻辑复杂的视图(如包含多表JOIN、GROUP BY、聚合函数的视图),可使用物化视图预先计算并存储结果。物化视图会定期刷新(如每日凌晨同步数据),查询时直接读取存储的结果,大幅减少运行时开销。
示例:创建物化视图存储销售数据的月度汇总结果,设置每日刷新:
CREATE MATERIALIZED VIEW sales_mv
BUILD IMMEDIATE
REFRESH COMPLETE ON DEMAND
AS
SELECT product_id, TO_CHAR(sale_date, 'YYYY-MM') AS month, SUM(amount) AS total_sales
FROM sales
GROUP BY product_id, TO_CHAR(sale_date, 'YYYY-MM');
需注意:物化视图会增加存储成本,需根据数据更新频率和查询需求平衡。
CREATE VIEW v1 AS SELECT * FROM v2 WHERE...),嵌套会导致查询时多次解析底层视图,增加执行复杂度。可将嵌套视图的定义合并为一个视图,或使用内联视图(将子查询直接嵌入主查询中)。UPPER()、ROUND())或DISTINCT(若底层查询已保证唯一性)。例如,若底层表employees的name列已唯一,无需在视图中使用SELECT DISTINCT name FROM employees。WITH子句(公用表表达式,CTE)提高可读性和性能。例如,将SELECT * FROM (SELECT department_id, AVG(salary) FROM employees GROUP BY department_id) WHERE avg_salary > 5000重写为带CTE的视图:CREATE OR REPLACE VIEW high_avg_salary_dept AS
WITH dept_avg AS (
SELECT department_id, AVG(salary) AS avg_salary
FROM employees
GROUP BY department_id
)
SELECT * FROM dept_avg WHERE avg_salary > 5000;
/*+ INDEX(table alias index name) */提示:CREATE OR REPLACE VIEW emp_dept_view AS
SELECT /*+ INDEX(e idx_emp_department_id) */ e.employee_id, e.name, d.department_name
FROM employees e
JOIN departments d ON e.department_id = d.department_id;
提示需谨慎使用,需通过EXPLAIN PLAN验证效果。若视图引用的底层表数据量较大,可对表进行分区(如按时间、地域、ID范围分区),然后创建分区视图将多个分区表联合起来。查询时,Oracle会自动根据查询条件选择对应的分区,减少扫描的数据量。
示例:按月份分区的sales表,创建分区视图:
CREATE VIEW sales_partitioned_view AS
SELECT * FROM sales_202501
UNION ALL
SELECT * FROM sales_202502
UNION ALL
SELECT * FROM sales_202503;
查询2025年1月的销售数据时,Oracle只会扫描sales_202501分区。
DBMS_STATS包为底层表收集统计信息(如表行数、块数、列值分布),确保优化器能生成最优执行计划。例如,收集employees表的统计信息:EXEC DBMS_STATS.GATHER_TABLE_STATS('HR', 'EMPLOYEES');
EXPLAIN PLAN或SQL Developer的“执行计划”工具查看视图查询的执行路径,重点关注全表扫描(FULL TABLE SCAN)、哈希连接(HASH JOIN)、**排序(SORT ORDER BY)**等高开销操作。例如,若执行计划显示视图查询对底层表进行了全表扫描,需检查是否缺失索引。ORDER BY子句(如CREATE VIEW v1 AS SELECT * FROM employees ORDER BY name),而查询时未指定排序,多余的排序会增加开销。仅在需要固定结果顺序时使用ORDER BY。WHERE条件过滤不必要的数据(如CREATE VIEW active_employees AS SELECT * FROM employees WHERE status = 'ACTIVE'),减少查询时返回的行数。SORT_AREA_SIZE),减少排序操作对磁盘的依赖(如临时表空间的使用)。:dept_id代替硬编码的10)减少SQL硬解析,提高视图查询的并发性能。