oracle不可更新的试图

本文介绍了在数据库中使用WITH READONLY属性创建视图的方法及其效果。通过对比两个视图V1和V2,演示了WITH READONLY如何阻止通过视图进行数据插入操作。

关键词:with read only

作用:用于指定所创建的试图不可以通过本视图更新表

 

执行一下SQL,创建表T,和两个试图V1,V2:

CREATE TABLE T(ID INTEGER);

CREATE VIEW V1 AS SELECT * FROM T;

CREATE VIEW V2 AS SELECT * FROM T WITH READ ONLY;

 

执行SQL:

INSERT INTO V1 VALUES(1);

--------------------

1 row created

 

 

执行SQL:

INSERT INTO V2 VALUES(1);

--------------------

提示错误

 

 

单独的SELECT语句不能使用WITH READ ONLY

SELECT * FROM T WITH READ ONLY;

将不能运行。

Oracle 数据库中,视图(View)是一个虚拟表,它基于一个或多个表的查询结果。通常情况下,视图本身并不存储数据,而是从底层的基表中动态检索数据。因此,更新视图中的数据实际上是对这些基表进行更新。 要成功地更新视图的数据,需要满足以下几个条件: 1. **视图必须是可更新的**:如果视图包含聚合函数(如 `SUM`、`COUNT`)、分组(`GROUP BY`)、集合操作符(如 `UNION`、`INTERSECT`)或者子查询,则该视图通常是不可更新的。 2. **更新语句只能影响一个基表**:如果视图连接了多个表,并且更新语句会影响多个表,则此更新将无法执行。 3. **视图定义中不能使用 `ROWNUM` 或伪列**:例如 `ROWNUM` 和 `ROWID` 会导致视图不可更新。 4. **基表字段必须存在于视图中**:如果你希望更新某个字段,该字段必须包含在视图的定义中。 ### 示例 假设有一个简单的视图 `employee_view`,其定义如下: ```sql CREATE OR REPLACE VIEW employee_view AS SELECT employee_id, first_name, last_name, salary FROM employees; ``` 可以通过以下 SQL 语句更新视图中的数据: ```sql UPDATE employee_view SET salary = salary * 1.1 WHERE employee_id = 101; ``` 这条语句会将 `employees` 表中 `employee_id` 为 `101` 的记录的薪资提高 10%。由于视图没有包含任何复杂的逻辑,它直接映射到单个表,因此可以成功更新。 ### 使用 `INSTEAD OF` 触发器处理复杂视图更新 对于涉及多个表的复杂视图,可以通过创建 `INSTEAD OF` 触发器来实现更新操作。例如,假设有两个表 `orders` 和 `customers`,并创建了一个联合视图 `order_customer_view`: ```sql CREATE OR REPLACE VIEW order_customer_view AS SELECT o.order_id, c.customer_id, c.name, o.amount FROM orders o JOIN customers c ON o.customer_id = c.customer_id; ``` 在这种情况下,直接更新视图可能会失败,因为 Oracle 无法确定如何修改底层的多张表。这时可以使用 `INSTEAD OF` 触发器: ```sql CREATE OR REPLACE TRIGGER update_order_customer INSTEAD OF UPDATE ON order_customer_view BEGIN -- 更新客户信息 IF :NEW.name != :OLD.name THEN UPDATE customers SET name = :NEW.name WHERE customer_id = :NEW.customer_id; END IF; -- 更新订单金额 IF :NEW.amount != :OLD.amount THEN UPDATE orders SET amount = :NEW.amount WHERE order_id = :NEW.order_id; END IF; END; / ``` 通过这种方式,即使视图涉及多个表,也可以自定义具体的更新逻辑。 需要注意的是,在启用某些功能时(如闪回日志等),数据库会产生额外的开销,因为系统必须记录所有对数据的更改以便支持恢复操作 [^2]。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值