我应该在Oracle SQL中创建一个触发器
- 将
department_amount
列添加到locations表 - 添加注释'包含该位置的部门数量'
- 创建一个触发器,它将在每次从部门插入/删除一行时更新所在位置的部门数量。
表:
CREATE TABLE departments
(
department_id NUMBER(4) PRIMARY KEY,
department_name VARCHAR2(30) NOT NULL,
manager_id NUMBER(6),
location_id NUMBER(4) NOT NULL
);
CREATE TABLE locations
(
location_id NUMBER(4) PRIMARY KEY,
street_address VARCHAR2(40),
postal_code VARCHAR2(12),
city VARCHAR2(30),
state_province VARCHAR2(25),
country_id CHAR(2) NOT NULL
);
回答你的问题
添加department_amount列到locations表
alter table locations add department_amount number ;
添加评论"包含的部门位置">
comment on column locations.deparment_amount is 'Contains the amount of departments in the location';
创建一个触发器,它将在每次从部门插入/删除一行时更新所在位置的部门数量。
create or replace trigger trg_loc
after insert or delete on departments
declare
begin
merge into locations t
using ( select count(department_id) as dpt_amount, location_id as loc_id
from departments b
group by location_id ) s
on (t.location_id = s.loc_id)
when matched then
update set t.department_amount = s.dpt_amount ;
end;
/
下面是一个数据库<>数据示例和触发器演示,当您为每个位置插入或删除一个部门时,更新locations
表中的department_amount
。
,db<的在小提琴
我觉得这个任务太不应该做了它没有任何作用。即使是训练也不行。
你要做的是
- 检查
locations.department_amount
列是否存在。您可以通过查看系统视图dba_tables
(或all_tables
或user_tables
,如果合适的话)来做到这一点。 - 如果该列不存在,通过
ALTER TABLE
创建它。然而,这是DDL,而不是DML,所以你必须通过EXECUTE IMMEDIATE
动态地运行它。 - 如果您刚刚创建了列,也创建了评论。
- 现在,在同一个触发器中,从
department_amount
中添加或减去1。这样就保证了第一个操作(导致创建列的操作)已经更新了它。
第1点到第3点只发生在语句级,而第4点应该发生在行级。由于这个原因,并且为了避免其他触发器的问题,这个触发器应该是复合触发器。
但是,如果您可以在数据库中创建触发器,为什么不能也添加列及其注释呢?为什么一定要编写触发器,让它检查列是否存在?如前所述,这是没有意义的,所以最好不要这样做。