【Oracle】视图
个人主页:Guiat
归属专栏:Oracle
文章目录
- 1. 视图基础概述
- 1.1 视图的概念与特点
- 1.2 视图的工作原理
- 1.3 视图的分类
- 2. 简单视图
- 2.1 创建简单视图
- 2.1.1 基本简单视图
- 2.1.2 带计算列的简单视图
- 2.2 简单视图的DML操作
- 2.2.1 通过视图进行INSERT操作
- 2.2.2 通过视图进行UPDATE操作
- 2.2.3 通过视图进行DELETE操作
- 3. 复杂视图
- 3.1 多表连接视图
- 3.1.1 员工部门视图
- 3.1.2 员工层级关系视图
- 3.2 聚合统计视图
- 3.2.1 部门统计视图
- 3.2.2 职位薪资分析视图
- 3.3 时间序列分析视图
- 3.3.1 年度招聘趋势视图
- 4. 视图的更新控制
- 4.1 WITH CHECK OPTION
- 4.1.1 基本CHECK OPTION
- 4.1.2 分级CHECK OPTION
- 4.2 WITH READ ONLY
- 5. 物化视图
- 5.1 基本物化视图
- 5.1.1 创建物化视图
- 5.1.2 自动刷新物化视图
- 5.2 快速刷新物化视图
- 5.2.1 创建物化视图日志
- 5.2.2 创建快速刷新物化视图
- 6. 视图管理与维护
- 6.1 查看视图信息
- 6.1.1 视图元数据查询
- 6.1.2 物化视图状态查询
- 6.2 视图性能优化
- 6.2.1 执行计划分析
- 6.2.2 视图性能优化建议
- 6.3 视图的修改和删除
- 6.3.1 修改视图
- 6.3.2 删除视图
- 7. 视图安全与权限
- 7.1 视图权限管理
- 7.1.1 授予视图权限
- 7.1.2 回收视图权限
- 7.2 行级安全(RLS)视图
- 7.2.1 创建安全视图
- 7.3 视图最佳实践
- 7.3.1 命名规范
- 7.3.2 设计原则
- 8. 实际应用案例
- 8.1 企业报表视图系统
- 8.1.1 销售业绩报表视图
- 8.1.2 客户分析视图
- 8.2 数据仓库视图层
- 8.2.1 维度视图
- 8.2.2 事实视图
正文
1. 视图基础概述
视图是Oracle数据库中的虚拟表,它是基于一个或多个表的查询结果集。视图不存储实际数据,而是存储查询定义,当访问视图时动态执行查询。
1.1 视图的概念与特点
1.2 视图的工作原理
1.3 视图的分类
2. 简单视图
简单视图基于单个表,通常可以进行DML操作。
2.1 创建简单视图
2.1.1 基本简单视图
-- 创建基本的简单视图
CREATE VIEW emp_basic_info AS
SELECT employee_id, first_name, last_name, email, hire_date
FROM employees;-- 创建带WHERE条件的简单视图
CREATE VIEW active_employees AS
SELECT employee_id, first_name, last_name, email, phone_number, hire_date, salary
FROM employees
WHERE hire_date >= DATE '2020-01-01';-- 创建带列别名的简单视图
CREATE VIEW emp_summary AS
SELECT employee_id AS emp_id,first_name || ' ' || last_name AS full_name,email AS email_address,salary AS monthly_salary,salary * 12 AS annual_salary,hire_date
FROM employees;-- 查看视图结构
DESCRIBE emp_basic_info;-- 查询视图数据
SELECT * FROM emp_basic_info WHERE employee_id < 110;
2.1.2 带计算列的简单视图
-- 创建包含计算列的视图
CREATE VIEW emp_salary_analysis AS
SELECT employee_id,first_name || ' ' || last_name AS employee_name,salary,salary * 12 AS annual_salary,CASE WHEN salary < 5000 THEN 'Low'WHEN salary BETWEEN 5000 AND 10000 THEN 'Medium'WHEN salary > 10000 THEN 'High'END AS salary_grade,ROUND(MONTHS_BETWEEN(SYSDATE, hire_date)) AS months_employed,ROUND(MONTHS_BETWEEN(SYSDATE, hire_date) / 12, 1) AS years_employed
FROM employees;-- 查询计算列视图
SELECT employee_name, salary_grade, annual_salary, years_employed
FROM emp_salary_analysis
WHERE salary_grade = 'High'
ORDER BY annual_salary DESC;
2.2 简单视图的DML操作
2.2.1 通过视图进行INSERT操作
-- 创建可插入的视图
CREATE VIEW emp_insert_view AS
SELECT employee_id, first_name, last_name, email, hire_date, job_id, department_id
FROM employees;-- 通过视图插入数据
INSERT INTO emp_insert_view (employee_id, first_name, last_name, email, hire_date, job_id, department_id
) VALUES (999, 'John', 'Doe', 'john.doe@company.com', SYSDATE, 'IT_PROG', 60
);-- 验证插入结果
SELECT * FROM emp_insert_view WHERE employee_id = 999;
SELECT * FROM employees WHERE employee_id = 999;
2.2.2 通过视图进行UPDATE操作
-- 通过视图更新数据
UPDATE emp_insert_view
SET email = 'john.doe.updated@company.com',job_id = 'IT_ADMIN'
WHERE employee_id = 999;-- 批量更新
UPDATE emp_salary_analysis
SET salary = salary * 1.05
WHERE salary_grade = 'Low';-- 验证更新结果
SELECT employee_id, employee_name, salary, salary_grade
FROM emp_salary_analysis
WHERE employee_id = 999;
2.2.3 通过视图进行DELETE操作
-- 通过视图删除数据
DELETE FROM emp_insert_view WHERE employee_id = 999;-- 验证删除结果
SELECT COUNT(*) FROM employees WHERE employee_id = 999;
3. 复杂视图
复杂视图基于多个表或包含函数、分组等复杂操作,通常是只读的。
3.1 多表连接视图
3.1.1 员工部门视图
-- 创建员工部门完整信息视图
CREATE VIEW emp_dept_detail AS
SELECT e.employee_id,e.first_name || ' ' || e.last_name AS employee_name,e.email,e.salary,e.hire_date,j.job_title,d.department_name,d.manager_id AS dept_manager_id,dm.first_name || ' ' || dm.last_name AS dept_manager_name,l.city,l.state_province,c.country_name
FROM employees e
JOIN jobs j ON e.job_id = j.job_id
JOIN departments d ON e.department_id = d.department_id
LEFT JOIN employees dm ON d.manager_id = dm.employee_id
JOIN locations l ON d.location_id = l.location_id
JOIN countries c ON l.country_id = c.country_id;-- 查询员工部门详细信息
SELECT employee_name, job_title, department_name, city, country_name
FROM emp_dept_detail
WHERE country_name = 'United States'
ORDER BY department_name, employee_name;
3.1.2 员工层级关系视图
-- 创建员工管理层级视图
CREATE VIEW emp_hierarchy AS
SELECT e.employee_id,e.first_name || ' ' || e.last_name AS employee_name,e.job_id,e.salary,e.hire_date,e.manager_id,m.first_name || ' ' || m.last_name AS manager_name,m.job_id AS manager_job_id,d.department_name,LEVEL AS hierarchy_level,SYS_CONNECT_BY_PATH(e.first_name || ' ' || e.last_name, ' -> ') AS hierarchy_path
FROM employees e
LEFT JOIN employees m ON e.manager_id = m.employee_id
JOIN departments d ON e.department_id = d.department_id
START WITH e.manager_id IS NULL
CONNECT BY PRIOR e.employee_id = e.manager_id;-- 查询组织层级结构
SELECT LPAD(' ', (hierarchy_level - 1) * 2) || employee_name AS org_structure,job_id,manager_name,department_name
FROM emp_hierarchy
WHERE department_name = 'Executive'
ORDER BY hierarchy_level, employee_name;
3.2 聚合统计视图
3.2.1 部门统计视图
-- 创建部门统计汇总视图
CREATE VIEW dept_statistics AS
SELECT d.department_id,d.department_name,d.location_id,l.city,COUNT(e.employee_id) AS employee_count,ROUND(AVG(e.salary), 2) AS avg_salary,MIN(e.salary) AS min_salary,MAX(e.salary) AS max_salary,SUM(e.salary) AS total_salary,ROUND(STDDEV(e.salary), 2) AS salary_stddev,MIN(e.hire_date) AS earliest_hire_date,MAX(e.hire_date) AS latest_hire_date
FROM departments d
LEFT JOIN employees e ON d.department_id = e.department_id
LEFT JOIN locations l ON d.location_id = l.location_id
GROUP BY d.department_id, d.department_name, d.location_id, l.city;-- 查询部门统计信息
SELECT department_name, employee_count,avg_salary,total_salary,city
FROM dept_statistics
WHERE employee_count > 0
ORDER BY avg_salary DESC;
3.2.2 职位薪资分析视图
-- 创建职位薪资分析视图
CREATE VIEW job_salary_analysis AS
SELECT j.job_id,j.job_title,COUNT(e.employee_id) AS position_count,ROUND(AVG(e.salary), 2) AS avg_salary,ROUND(MEDIAN(e.salary), 2) AS median_salary,MIN(e.salary) AS min_salary,MAX(e.salary) AS max_salary,j.min_salary AS job_min_salary,j.max_salary AS job_max_salary,ROUND(AVG(e.salary) - j.min_salary, 2) AS avg_above_min,ROUND(j.max_salary - AVG(e.salary), 2) AS avg_below_max,ROUND((AVG(e.salary) - j.min_salary) / (j.max_salary - j.min_salary) * 100, 1) AS salary_position_pct
FROM jobs j
LEFT JOIN employees e ON j.job_id = e.job_id
GROUP BY j.job_id, j.job_title, j.min_salary, j.max_salary;-- 查询职位薪资分析
SELECT job_title,position_count,avg_salary,median_salary,salary_position_pct || '%' AS position_in_range
FROM job_salary_analysis
WHERE position_count > 0
ORDER BY avg_salary DESC;
3.3 时间序列分析视图
3.3.1 年度招聘趋势视图
-- 创建年度招聘趋势分析视图
CREATE VIEW yearly_hiring_trends AS
SELECT hire_year,total_hired,LAG(total_hired, 1) OVER (ORDER BY hire_year) AS prev_year_hired,total_hired - LAG(total_hired, 1) OVER (ORDER BY hire_year) AS year_over_year_change,ROUND((total_hired - LAG(total_hired, 1) OVER (ORDER BY hire_year)) / LAG(total_hired, 1) OVER (ORDER BY hire_year) * 100, 1) AS yoy_change_pct,avg_starting_salary,LAG(avg_starting_salary, 1) OVER (ORDER BY hire_year) AS prev_avg_salary,ROUND(avg_starting_salary - LAG(avg_starting_salary, 1) OVER (ORDER BY hire_year), 2) AS salary_change
FROM (SELECT EXTRACT(YEAR FROM hire_date) AS hire_year,COUNT(*) AS total_hired,ROUND(AVG(salary), 2) AS avg_starting_salaryFROM employeesGROUP BY EXTRACT(YEAR FROM hire_date)
);-- 查询招聘趋势
SELECT hire_year,total_hired,CASE WHEN yoy_change_pct > 0 THEN '+' || yoy_change_pct || '%'WHEN yoy_change_pct < 0 THEN yoy_change_pct || '%'ELSE 'N/A'END AS growth_rate,avg_starting_salary,salary_change
FROM yearly_hiring_trends
ORDER BY hire_year;
4. 视图的更新控制
4.1 WITH CHECK OPTION
WITH CHECK OPTION确保通过视图进行的DML操作符合视图的WHERE条件。
4.1.1 基本CHECK OPTION
-- 创建带CHECK OPTION的视图
CREATE VIEW high_salary_employees AS
SELECT employee_id, first_name, last_name, salary, department_id
FROM employees
WHERE salary > 8000
WITH CHECK OPTION;-- 尝试插入符合条件的记录(成功)
INSERT INTO high_salary_employees
VALUES (998, 'Jane', 'Smith', 9000, 60);-- 尝试插入不符合条件的记录(失败)
-- 以下操作会产生错误:ORA-01402: view WITH CHECK OPTION where-clause violation
BEGININSERT INTO high_salary_employees VALUES (997, 'Bob', 'Johnson', 5000, 60);
EXCEPTIONWHEN OTHERS THENDBMS_OUTPUT.PUT_LINE('错误: ' || SQLERRM);
END;
/-- 尝试更新为不符合条件的值(失败)
BEGINUPDATE high_salary_employees SET salary = 3000 WHERE employee_id = 998;
EXCEPTIONWHEN OTHERS THENDBMS_OUTPUT.PUT_LINE('更新错误: ' || SQLERRM);
END;
/
4.1.2 分级CHECK OPTION
-- 创建基础视图
CREATE VIEW dept_employees AS
SELECT employee_id, first_name, last_name, salary, department_id
FROM employees
WHERE department_id = 60;-- 创建基于视图的视图,带CHECK OPTION
CREATE VIEW senior_dept_employees AS
SELECT employee_id, first_name, last_name, salary, department_id
FROM dept_employees
WHERE salary > 7000
WITH CHECK OPTION;-- 测试分级检查
INSERT INTO senior_dept_employees
VALUES (996, 'Alice', 'Brown', 8500, 60); -- 成功-- 清理测试数据
DELETE FROM employees WHERE employee_id IN (996, 998);
4.2 WITH READ ONLY
WITH READ ONLY选项创建只读视图,禁止任何DML操作。
-- 创建只读视图
CREATE VIEW emp_salary_report AS
SELECT d.department_name,e.employee_id,e.first_name || ' ' || e.last_name AS employee_name,e.salary,e.hire_date,RANK() OVER (PARTITION BY d.department_id ORDER BY e.salary DESC) AS salary_rank
FROM employees e
JOIN departments d ON e.department_id = d.department_id
WITH READ ONLY;-- 查询只读视图
SELECT department_name, employee_name, salary, salary_rank
FROM emp_salary_report
WHERE salary_rank <= 3
ORDER BY department_name, salary_rank;-- 尝试更新只读视图(会失败)
BEGINUPDATE emp_salary_report SET salary = 10000 WHERE employee_id = 100;
EXCEPTIONWHEN OTHERS THENDBMS_OUTPUT.PUT_LINE('只读视图错误: ' || SQLERRM);
END;
/
5. 物化视图
物化视图是将查询结果物理存储的视图,可以显著提高复杂查询的性能。
5.1 基本物化视图
5.1.1 创建物化视图
-- 创建基本物化视图
CREATE MATERIALIZED VIEW mv_dept_summary
BUILD IMMEDIATE
REFRESH COMPLETE ON DEMAND
AS
SELECT d.department_id,d.department_name,COUNT(e.employee_id) AS emp_count,ROUND(AVG(e.salary), 2) AS avg_salary,SUM(e.salary) AS total_salary
FROM departments d
LEFT JOIN employees e ON d.department_id = e.department_id
GROUP BY d.department_id, d.department_name;-- 查询物化视图
SELECT * FROM mv_dept_summary
WHERE emp_count > 0
ORDER BY avg_salary DESC;-- 手动刷新物化视图
EXEC DBMS_MVIEW.REFRESH('mv_dept_summary');
5.1.2 自动刷新物化视图
-- 创建自动刷新的物化视图
CREATE MATERIALIZED VIEW mv_monthly_stats
BUILD IMMEDIATE
REFRESH COMPLETE ON COMMIT
AS
SELECT EXTRACT(YEAR FROM hire_date) AS hire_year,EXTRACT(MONTH FROM hire_date) AS hire_month,COUNT(*) AS employees_hired,ROUND(AVG(salary), 2) AS avg_starting_salary
FROM employees
GROUP BY EXTRACT(YEAR FROM hire_date), EXTRACT(MONTH FROM hire_date);-- 当基础表发生变化时,物化视图会自动刷新
INSERT INTO employees (employee_id, first_name, last_name, email, hire_date, job_id, salary, department_id)
VALUES (995, 'Test', 'Employee', 'test@company.com', SYSDATE, 'IT_PROG', 6000, 60);COMMIT;-- 查看更新后的物化视图
SELECT * FROM mv_monthly_stats
WHERE hire_year = EXTRACT(YEAR FROM SYSDATE)
ORDER BY hire_year, hire_month;-- 清理测试数据
DELETE FROM employees WHERE employee_id = 995;
COMMIT;
5.2 快速刷新物化视图
快速刷新只更新发生变化的部分,需要物化视图日志。
5.2.1 创建物化视图日志
-- 为基础表创建物化视图日志
CREATE MATERIALIZED VIEW LOG ON employees
WITH ROWID, SEQUENCE (employee_id, department_id, salary)
INCLUDING NEW VALUES;CREATE MATERIALIZED VIEW LOG ON departments
WITH ROWID, SEQUENCE (department_id, department_name)
INCLUDING NEW VALUES;
5.2.2 创建快速刷新物化视图
-- 创建支持快速刷新的物化视图
CREATE MATERIALIZED VIEW mv_dept_summary_fast
BUILD IMMEDIATE
REFRESH FAST ON DEMAND
AS
SELECT d.department_id,d.department_name,COUNT(e.employee_id) AS emp_count,SUM(e.salary) AS total_salary,COUNT(*) AS row_count
FROM departments d, employees e
WHERE d.department_id = e.department_id(+)
GROUP BY d.department_id, d.department_name;-- 进行一些更改
UPDATE employees SET salary = salary + 100 WHERE employee_id = 100;-- 快速刷新物化视图
EXEC DBMS_MVIEW.REFRESH('mv_dept_summary_fast', 'F');-- 查看刷新后的结果
SELECT * FROM mv_dept_summary_fast ORDER BY department_id;
6. 视图管理与维护
6.1 查看视图信息
6.1.1 视图元数据查询
-- 查看用户拥有的所有视图
SELECT view_name, text_length, read_only
FROM user_views
ORDER BY view_name;-- 查看视图的详细定义
SELECT view_name, text
FROM user_views
WHERE view_name = 'EMP_DEPT_DETAIL';-- 查看视图的列信息
SELECT column_name, data_type, nullable
FROM user_tab_columns
WHERE table_name = 'EMP_DEPT_DETAIL'
ORDER BY column_id;-- 查看视图的依赖关系
SELECT name, type, referenced_name, referenced_type
FROM user_dependencies
WHERE name = 'EMP_DEPT_DETAIL';
6.1.2 物化视图状态查询
-- 查看物化视图信息
SELECT mview_name, refresh_mode, refresh_method, build_mode, last_refresh_date, compile_state
FROM user_mviews;-- 查看物化视图刷新历史
SELECT mview_name, refresh_method, start_time, end_time, elapsed_time
FROM user_mview_refresh_times
WHERE mview_name = 'MV_DEPT_SUMMARY'
ORDER BY start_time DESC;-- 查看物化视图日志信息
SELECT log_table, master, log_trigger, rowids, primary_key, object_id
FROM user_mview_logs;
6.2 视图性能优化
6.2.1 执行计划分析
-- 分析视图查询的执行计划
EXPLAIN PLAN FOR
SELECT employee_name, department_name, salary
FROM emp_dept_detail
WHERE salary > 8000
ORDER BY salary DESC;SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);-- 比较直接查询和视图查询的性能
EXPLAIN PLAN FOR
SELECT e.first_name || ' ' || e.last_name AS employee_name,d.department_name,e.salary
FROM employees e
JOIN departments d ON e.department_id = d.department_id
WHERE e.salary > 8000
ORDER BY e.salary DESC;SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);
6.2.2 视图性能优化建议
-- 创建优化的视图,包含提示
CREATE OR REPLACE VIEW emp_dept_optimized AS
SELECT /*+ USE_NL(e d) INDEX(e emp_department_ix) */e.employee_id,e.first_name || ' ' || e.last_name AS employee_name,e.salary,d.department_name
FROM employees e
JOIN departments d ON e.department_id = d.department_id;-- 为经常查询的列创建索引
CREATE INDEX emp_salary_idx ON employees(salary);
CREATE INDEX emp_dept_idx ON employees(department_id);
6.3 视图的修改和删除
6.3.1 修改视图
-- 使用OR REPLACE修改视图定义
CREATE OR REPLACE VIEW emp_basic_info AS
SELECT employee_id, first_name, last_name, email, hire_date,salary, -- 新增列department_id -- 新增列
FROM employees
WHERE hire_date >= DATE '2010-01-01'; -- 新增条件-- 验证视图修改
DESCRIBE emp_basic_info;
SELECT * FROM emp_basic_info WHERE rownum <= 5;
6.3.2 删除视图
-- 删除普通视图
DROP VIEW emp_summary;-- 删除物化视图
DROP MATERIALIZED VIEW mv_dept_summary;-- 删除物化视图日志
DROP MATERIALIZED VIEW LOG ON employees;
DROP MATERIALIZED VIEW LOG ON departments;-- 验证删除结果
SELECT view_name FROM user_views WHERE view_name IN ('EMP_SUMMARY');
SELECT mview_name FROM user_mviews WHERE mview_name = 'MV_DEPT_SUMMARY';
7. 视图安全与权限
7.1 视图权限管理
7.1.1 授予视图权限
-- 创建用于演示的视图
CREATE VIEW public_emp_info AS
SELECT employee_id, first_name, last_name, email, hire_date
FROM employees;-- 授予其他用户查询权限
GRANT SELECT ON public_emp_info TO other_user;-- 授予更新权限
GRANT UPDATE ON public_emp_info TO other_user;-- 授予所有权限
GRANT ALL ON public_emp_info TO privileged_user;-- 查看授予的权限
SELECT grantee, privilege, grantable
FROM user_tab_privs
WHERE table_name = 'PUBLIC_EMP_INFO';
7.1.2 回收视图权限
-- 回收特定权限
REVOKE UPDATE ON public_emp_info FROM other_user;-- 回收所有权限
REVOKE ALL ON public_emp_info FROM other_user;
7.2 行级安全(RLS)视图
7.2.1 创建安全视图
-- 创建部门级安全视图
CREATE VIEW secure_emp_view AS
SELECT employee_id, first_name, last_name, email, salary, department_id
FROM employees
WHERE department_id IN (SELECT department_id FROM user_dept_access WHERE username = USER
);-- 创建基于角色的视图
CREATE VIEW role_based_emp_view AS
SELECT employee_id, first_name, last_name, email,CASE WHEN USER IN (SELECT username FROM hr_managers) THEN salaryELSE NULLEND AS salary,department_id
FROM employees;
7.3 视图最佳实践
7.3.1 命名规范
-- 推荐的视图命名规范
CREATE VIEW v_employee_summary AS ...; -- 前缀 v_
CREATE VIEW emp_dept_vw AS ...; -- 后缀 _vw
CREATE MATERIALIZED VIEW mv_sales_summary AS ...; -- 物化视图前缀 mv_-- 业务相关的命名
CREATE VIEW finance_employee_view AS ...; -- 财务部门员工视图
CREATE VIEW active_projects_view AS ...; -- 活跃项目视图
7.3.2 设计原则
8. 实际应用案例
8.1 企业报表视图系统
8.1.1 销售业绩报表视图
-- 创建销售业绩综合报表视图
CREATE VIEW sales_performance_report AS
SELECT s.salesperson_id,e.first_name || ' ' || e.last_name AS salesperson_name,d.department_name,EXTRACT(YEAR FROM s.sale_date) AS sale_year,EXTRACT(QUARTER FROM s.sale_date) AS sale_quarter,COUNT(s.sale_id) AS total_sales,SUM(s.amount) AS total_revenue,ROUND(AVG(s.amount), 2) AS avg_sale_amount,RANK() OVER (PARTITION BY EXTRACT(YEAR FROM s.sale_date), EXTRACT(QUARTER FROM s.sale_date)ORDER BY SUM(s.amount) DESC) AS performance_rank
FROM sales s
JOIN employees e ON s.salesperson_id = e.employee_id
JOIN departments d ON e.department_id = d.department_id
GROUP BY s.salesperson_id, e.first_name, e.last_name, d.department_name,EXTRACT(YEAR FROM s.sale_date), EXTRACT(QUARTER FROM s.sale_date);
8.1.2 客户分析视图
-- 创建客户价值分析视图
CREATE VIEW customer_value_analysis AS
SELECT c.customer_id,c.customer_name,c.registration_date,COUNT(o.order_id) AS total_orders,SUM(o.order_amount) AS total_spent,ROUND(AVG(o.order_amount), 2) AS avg_order_value,MAX(o.order_date) AS last_order_date,ROUND(MONTHS_BETWEEN(SYSDATE, MAX(o.order_date)), 1) AS months_since_last_order,CASE WHEN SUM(o.order_amount) > 10000 THEN 'VIP'WHEN SUM(o.order_amount) > 5000 THEN 'Premium'WHEN SUM(o.order_amount) > 1000 THEN 'Regular'ELSE 'Basic'END AS customer_tier,CASE WHEN MONTHS_BETWEEN(SYSDATE, MAX(o.order_date)) <= 3 THEN 'Active'WHEN MONTHS_BETWEEN(SYSDATE, MAX(o.order_date)) <= 12 THEN 'At Risk'ELSE 'Inactive'END AS customer_status
FROM customers c
LEFT JOIN orders o ON c.customer_id = o.customer_id
GROUP BY c.customer_id, c.customer_name, c.registration_date;
8.2 数据仓库视图层
8.2.1 维度视图
-- 时间维度视图
CREATE VIEW dim_time AS
SELECT DISTINCTTRUNC(date_column) AS date_key,EXTRACT(YEAR FROM date_column) AS year,EXTRACT(QUARTER FROM date_column) AS quarter,EXTRACT(MONTH FROM date_column) AS month,EXTRACT(DAY FROM date_column) AS day,TO_CHAR(date_column, 'Day') AS day_name,TO_CHAR(date_column, 'Month') AS month_name,CASE WHEN TO_CHAR(date_column, 'D') IN ('1', '7') THEN 'Y' ELSE 'N' END AS is_weekend
FROM (SELECT hire_date AS date_column FROM employeesUNIONSELECT order_date FROM orders
);-- 产品维度视图
CREATE VIEW dim_product AS
SELECT p.product_id,p.product_name,p.product_code,c.category_name,c.category_id,p.unit_price,p.cost_price,p.unit_price - p.cost_price AS profit_margin,CASE WHEN p.unit_price - p.cost_price > 100 THEN 'High Margin'WHEN p.unit_price - p.cost_price > 50 THEN 'Medium Margin'ELSE 'Low Margin'END AS margin_category
FROM products p
JOIN categories c ON p.category_id = c.category_id;
8.2.2 事实视图
-- 销售事实视图
CREATE VIEW fact_sales AS
SELECT s.sale_id,s.sale_date,s.customer_id,s.product_id,s.salesperson_id,s.quantity,s.unit_price,s.total_amount,s.discount_amount,s.total_amount - s.discount_amount AS net_amount,p.cost_price * s.quantity AS total_cost,(s.total_amount - s.discount_amount) - (p.cost_price * s.quantity) AS profit
FROM sales s
JOIN products p ON s.product_id = p.product_id;
通过这个全面的Oracle视图教程,我们涵盖了从基础概念到高级应用的所有重要方面。视图是Oracle数据库中非常强大的工具,正确使用可以显著提高数据安全性、查询效率和系统维护性。在实际应用中,应该根据具体需求选择合适的视图类型,并遵循最佳实践来设计和维护视图。
结语
感谢您的阅读!期待您的一键三连!欢迎指正!
相关文章:

【Oracle】视图
个人主页:Guiat 归属专栏:Oracle 文章目录 1. 视图基础概述1.1 视图的概念与特点1.2 视图的工作原理1.3 视图的分类 2. 简单视图2.1 创建简单视图2.1.1 基本简单视图2.1.2 带计算列的简单视图 2.2 简单视图的DML操作2.2.1 通过视图进行INSERT操作2.2.2 通…...
数据库 MongoDB (NoSQL) 与 MySQL (SQL) 的写法对比
MongoDB (NoSQL) 与 MySQL (SQL) 的写法对比及优劣势分析 基本概念差异 MySQL/SQL:关系型数据库,使用结构化查询语言(SQL),数据以表格形式存储,有预定义的模式(schema)MongoDB/NoSQL:文档型数据库,无固定…...
基于粒子滤波的PSK信号解调实现
基于粒子滤波的PSK信号解调实现 一、引言 相移键控(PSK)是数字通信中广泛应用的调制技术。在非高斯噪声和动态相位偏移环境下,传统锁相环(PLL)性能受限。粒子滤波(Particle Filter)作为一种序列蒙特卡洛方法,能有效处理非线性/非高斯系统的状态估计问题。本文将详细阐…...

更强劲,更高效:智源研究院开源轻量级超长视频理解模型Video-XL-2
长视频理解是多模态大模型关键能力之一。尽管OpenAI GPT-4o、Google Gemini等私有模型已在该领域取得显著进展,当前的开源模型在效果、计算开销和运行效率等方面仍存在明显短板。近日,智源研究院联合上海交通大学等机构,正式发布新一代超长视…...

2025.6.3学习日记 Nginx 基本概念 配置 指令 文件
1.初始nginx Nginx(发音为 “engine x”)是一款高性能的开源 Web 服务器软件,同时也具备反向代理、负载均衡、邮件代理等功能。它由俄罗斯工程师 Igor Sysoev 开发,最初用于解决高并发场景下的性能问题,因其轻量级、高…...

【连接器专题】案例:产品测试顺序表解读与应用
在查看SD卡座连接器的规格书,一些测试报告时,你可能会看到如下一张产品测试顺序表。为什么会出现一张测试顺序表呢? 测试顺序表的使用其实定义测试环节的验证的“路线图”和“游戏规则”,本文就以我人个经验带领大家一起看懂这张表并理解其设计逻辑。 测试顺序表结构 测试…...

星动纪元的机器人大模型 VPP,泛化能力效果如何?与 VLA 技术的区别是什么?
点击上方关注 “终端研发部” 设为“星标”,和你一起掌握更多数据库知识 VPP 利用了大量互联网视频数据进行训练,直接学习人类动作,减轻了对于高质量机器人真机数据的依赖,且可在不同人形机器人本体之间自如切换,这有望…...

4000万日订单背后,饿了么再掀即时零售的“效率革命”
当即时零售转向价值深耕,赢面就是综合实力的强弱。 文|郭梦仪 编|王一粟 在硝烟弥漫的外卖行业“三国杀”中,饿了么与淘宝闪购的日订单量竟然突破了4000万单。 而距淘宝闪购正式上线,还不到一个月。 在大额福利优惠…...

入门AJAX——XMLHttpRequest(Get)
一、什么是 AJAX AJAX Asynchronous JavaScript And XML(异步的 JavaScript 和 XML)。 1、XML与异步JS XML: 是一种比较老的前后端数据传输格式(已经几乎被 JSON 代替)。它的格式与HTML类似,通过严格的闭合自定义标…...

5分钟申请edu邮箱【方案本周有效】
这篇文章主要展示的是成果。如果你是第1次看见我的内容,具体的步骤请翻看往期的两篇作品。先看更正补全,再看下一个。 建议你边看边操作。 【更正补全】edu教育申请通过方案 本周 edu教育邮箱注册可行方案 #edu邮箱 伟大无需多言 我已经验证了四个了…...

闲谈PMIC和SBC
今天不卷,简单写点。 在ECU设计里,供电芯片选型是逃不开的话题,所以聊聊PMIC或者SBC的各自特点,小小总结下。 PMIC,全称Power Management Intergrated Circuits,听名字就很专业:电源管理&…...

Java垃圾回收机制深度解析:从理论到实践的全方位指南
Java垃圾回收(GC)是Java虚拟机(JVM)的核心功能,它自动管理内存分配与回收,避免了C/C中常见的内存泄漏问题。本文将深入剖析Java垃圾回收的工作原理、算法实现、收集器类型及调优策略,助你全面掌握JVM内存管理的精髓。 一、垃圾回收基础概念 …...
Ubuntu系统 | 本地部署ollama+deepseek
1、Ollama介绍 Ollama是由Llama开发团队推出的开源项目,旨在为用户提供高效、灵活的本地化大型语言模型(LLM)运行环境。作为Llama系列模型的重要配套工具,Ollama解决了传统云服务对计算资源和网络连接的依赖问题,让用户能够在个人电脑或私有服务器上部署和运行如Llama 3等…...

论文阅读:CLIP:Learning Transferable Visual Models From Natural Language Supervision
从自然语言监督中学习可迁移的视觉模型 虽然有点data/gpu is all you need的味道,但是整体实验和谈论丰富度上还是很多的,也是一篇让我多次想放弃的文章,因为真的是非常长的原文和超级多的实验讨论,隔着屏幕感受到了实验的工作量之…...

在图像分析算法部署中应对流行趋势的变化|文献速递-深度学习医疗AI最新文献
Title 题目 Navigating prevalence shifts in image analysis algorithm deployment 在图像分析算法部署中应对流行趋势的变化 01 文献速递介绍 机器学习(ML)已开始革新成像研究与实践的诸多领域。然而,医学图像分析领域存在显著的转化鸿…...

CAMEL-AI开源自动化任务执行助手OWL一键整合包下载
OWL 是由 CAMEL-AI 团队开发的开源多智能体协作框架,旨在通过动态智能体交互实现复杂任务的自动化处理,在 GAIA 基准测试中以 69.09 分位列开源框架榜首,被誉为“Manus 的开源平替”。我基于当前最新版本制作了免安装一键启动整合包。 CAMEL-…...
Selenium 中 JavaScript 点击的优势及使用场景
*在 Selenium 自动化测试中,使用 JavaScript 执行点击操作(如driver.execute_script("arguments[0].click();", element))相比直接调用element.click()有以下几个主要优势: 1. 绕过元素不可点击的限制 问题场景&#x…...

Linux系统-基本指令(5)
文章目录 mv 指令cat 指令(查看小文件)知识点(简单阐述日志)more 和 less 指令(查看大文件)head 和 tail 指令(跟查看文件有关)知识点(管道)时间相关的指令&a…...
C++ set数据插入、set数据查找、set数据删除、set数据统计、set排序规则、代码练习1、2
set数据插入,代码见下 #include<iostream> #include<set> #include<vector>using namespace std;void printSet(const set<int>& s) {for (set<int>::const_iterator it s.begin(); it ! s.end(); it) {cout << *it <…...
[android]MT6835 Android 指令启动MT6631 wifi操作说明
问题说明 MT6835使用指令启动wifi 使用andorid指令启动 2.4G启动方式 cmd wifi start-softap ctltest wpa2 11111111 -b 2 5G启动指令 cmd wifi start-softap ctltest wpa2 11111111 -b 5 使用linux指令启动 指令启动wifi 新建br-lan brctl addbr br-lan 关闭wifi a…...

C# winform教程(二)
一、基础控件 常用的基础控件主要有按钮,文本,文本输入,组,进度条,等等。 基础控件 名称含义详细用法Button按钮Buttoncheckbox多选按钮Combobox下拉选择groupbox组控件label标签,显示文字panel控件集合&a…...
Java详解LeetCode 热题 100(25):LeetCode 141. 环形链表(Linked List Cycle)详解
文章目录 1. 题目描述1.1 链表节点定义 2. 理解题目2.1 环形链表的可视化2.2 核心难点 3. 解法一:HashSet 标记访问法3.1 算法思路3.2 Java代码实现3.3 详细执行过程演示3.4 执行结果示例3.5 复杂度分析3.6 优缺点分析 4. 解法二:快慢指针法(…...

【仿生机器人】刀剑神域计划——仿生机器人.亚丝娜
我在做仿生机器人头,硬件部分已经搭建完毕,包括头部和颈部,用的23个舵机驱动机器人做表情,也支持头部的旋转(就是颈部的功能),安装了摄像头在眼睛中,还有麦克风接受周围环境声音&…...

ARM架构推理Stable Diffusiond
代码仓库: https://github.com/siutin/stable-diffusion-webui-docker.git Docker容器地址: https://hub.docker.com/r/siutin/stable-diffusion-webui-docker/tags git clone https://github.com/siutin/stable-diffusion-webui-docker.git cd stabl…...

仓颉项目调试配置与多文件场景下的问题解析
1. 调试配置指南 在 VS Code 中配置好仓颉开发工具链后,只需按下 F5 或 Fn F5 即可启动调试。 在 CodeArts IDE for Cangjie 中,需先通过右上角的 编辑配置 -> 新增配置项 -> 选择 Cangjie (cjdb) Debug -> 选择 launch 模式 -> 点击 确认…...
Easyui悬停组件
文章目录 一、EasyUI 官方悬停解决方案:Tooltip 组件1. 基础用法2. 高级配置项 二、进阶场景:Datagrid 表格悬停扩展1. 监听行事件2. 第三方扩展包(流云大神版) 三、自定义悬停样式四、常见问题解决 在EasyUI中,没有直…...

MySQL 8.0 OCP 英文题库解析(十)
Oracle 为庆祝 MySQL 30 周年,截止到 2025.07.31 之前。所有人均可以免费考取原价245美元的MySQL OCP 认证。 从今天开始,将英文题库免费公布出来,并进行解析,帮助大家在一个月之内轻松通过OCP认证。 本期公布试题81~90 试题81:…...

Python Pytest
1.Pytest用例发现规则 1.1 模块名(python文件)名必须以 test_ 开头或 _test 结尾,如 test_case,case_test,下划线都不能少 1.2 模块不能放在 . 开头的隐藏目录或者叫 venv的目录下,virtual environment,叫venv1都可以…...
金属膜电阻和碳膜电阻
1、性能比较 特性金属膜电阻对比碳膜电阻精度0.1% ~ 1%5% ~ 10%温度系数15 ~ 50 ppm/℃(极低漂移)200 ~ 1000 ppm/℃噪声0.1 μV/V 以下(超低噪声)1~5 μV/V(中高频噪声显著)高频特性寄生电感/电容小&…...
DNS (Domain Name System) 域名系统 将域名解析为 IP 地址
✅ DNS 服务器是指什么? **DNS 服务器(Domain Name System Server)是一个将域名(如 www.baidu.com)解析为 IP 地址(如 220.181.38.150)**的服务器。 🧠 一句话理解: DNS…...