名为 T1 的表,其值为
Col1 Col2 Col3
Rs1 S S2
Rs2 SX S3
Rs3 S S2
从csv中,我需要在表中插入一些值,每个列的值分别为Rs4,SX和S3。
我需要应用具有以下约束条件的支票。
oracle的查询是什么?如果上述条件为真,那么我需要运行一个准备好的插入查询。它如何验证?
PS:我们无法创建另一个表。
答案 0 :(得分:1)
在得知我完全错过了ORACLE标签之后,不得不做一点发现。了解你不知道的事情对我来说非常重要。这篇文章应该有很大的不同。
ORACLE检查的基本问题
- 无法在SQL视图上定义检查约束。在表上定义的检查约束必须仅引用其中的列 表。它不能引用其他表中的列。
- 检查约束不能包含SQL子查询。
- 可以在SQL CREATE TABLE语句或SQL ALTER TABLE语句中定义检查约束。
重新解决问题
显然,业务要求尚未完全解释。
重新解决方案
虽然添加额外的表已被拒绝,但是可以添加ID列吗?假设Col1不是(Col2,COl3)子集唯一的,那么您可以添加一个真正的ID列,以满足规范化的需要,同时在查询中提供真正的索引功能。
Col1 Col2 Col3 Col4
Rs1 S S2 1
Rs2 SX S3 2
Rs3 S S2 1
要清楚,Col4仍然是一个ID,因为Col2,Col3的值由Col4决定。 (Col2,Col3) 1:1 Col4
。
- 多个CHECK约束,每个约束都有一个简单的条件强制执行 单个业务规则,优于单个CHECK约束 执行多个业务规则的复杂条件ORACLE - Constraint
- 单个列可以有多个引用的CHECK约束 列中的定义。 CHECK的数量没有限制 您可以在列上定义的约束。 ORACLE - Data Integrity
如果你可以通过猴子的爱来添加一个专栏...... ,请做...它不仅会让你的生活变得更轻松,而且你也可以让桌面非常高效地查询。但是,对于本文的其余部分,我将假设您无法添加列:
重新制定约束中的问题
写出检查理论
如果Col1在{(col2,col3)}中确实是唯一的,那么以下内容已经有效:
ALTER TABLE EXAMPLE3
ADD CONSTRAINT ch_example3_3way UNIQUE (C, D, X) --only works if these valus never repeat.
SARG
,否则1根本无法工作。任何Col1 = Col1
或Col1 IN Col1
都与写1 = 1相同。ON TRIGGERS
ORACLE
车道让我警告不要使用。 ORACLE
:
- 不要创建递归触发器。 例如,如果在上创建了AFTER UPDATE语句触发器 employees表,触发器本身发出UPDATE语句 在employees表中,触发器以递归方式触发,直到它用完为止 记忆
- 明智地在DATABASE上使用触发器。每次创建触发器的事件发生时,都会为每个用户执行它们
其他问题包括:TOADWORLD - ORACLE WIKI
- 未编译 - STORED PROC可以重复使用缓存计划
- 没有SELECT触发器支持
- 完成触发失败
- 已禁用触发器
- 无版本控制
- 更新栏目
- 不支持SYS表触发器
- 变异触发器
- 隐藏行为
仍然有TRIGGER
的优点,你仍然可以通过使用查询的第一个结果
SELECT Col2, Col3 FROM T1 WHERE ROWNUM = 1
与插入的值* new。* Col2,* new。* Col3进行比较,但这需要触发器每次插入一行...重新编译和一切,。我非常谨慎避免。
STORED PROCS
无论你怎么想STORED PROCEDURES
,我建议你再考虑一下。 Function
,DML
,DDL
,database management
,RECURSIVE LOGIC
,sp_executesql
以及更远的所有内容都可以通过{{1}完成}。
PROC
编译一次,可以重用查询计划缓存,提供更好的性能。PROC
,TRIGGERS
框架,应用程序及其他内容中。ORM
,ETL
,安全性和发现。 Resource management
通常通过存储过程运行。ORACLE的独特优势
也许已经忘记了,请考虑这是ORACLE,它允许您通过插入Views
CONSTRAINTS
来暂停CONSTRAINT
。从DEFFERABLE
专家的角度来看,这实际上是从你唯一的表格中制作一个临时表...这在你有限ETL
权利的困境中非常甜蜜。
结束评论
有一些有效的方法可以删除数据中的重复项。
DDL
最后,我最后一次尝试rowid。不幸的是,时间很晚,ORACLE的免费COMPILER无益。但我认为这个想法很重要。
DELETE FROM T1
WHERE rowid NOT IN
(SELECT MAX(rowid)
FROM T1
GROUP BY Col1, Col2, Col3);
答案 1 :(得分:1)
最后,我能够通过一些选择查询解决问题,如果应用了条件则很少。我在存储过程中完成了这个。
SELECT count(col3)
INTO V_exist_value
FROM T3
WHERE col3's value = Variable_col3
AND col1's value <> Variable_col1
AND col2's value = Variable_col2;
IF (V_exist_value >= 1) THEN
INSERT INTO T3 (col1, col2, col3)
VALUES (Variable_col1, Variable_col2, Variable_col3);
ELSE
SELECT count(col3)
INTO V_exist_value1
FROM T3
WHERE col3's value = Variable_col3;
IF (V_exist_value1 = 0) THEN
INSERT INTO T3 (col1, col2, col3)
VALUES (Variable_col1, Variable_col2, Variable_col3);
ELSE
RAISE Exception_col3_value_exists;
END IF;
END IF;
答案 2 :(得分:0)
如果您不想使用触发器,则必须对表格进行标准化。
T1_PAIRS
- 将存储所有允许的对(col2,col3)。col2
中的T1_PAIRS
列上创建唯一约束 - 此约束仅允许COL2
的唯一值 - 例如,不超过一个S3
值在所有对中使用==&gt;这强制执行规则:“一个S3只能属于一个SX”( col2, col3 )
中的T1_PAIRS
列上创建主键。( col2, col3 )
表中T1
创建引用T1_PAIRS
表主键的外键约束。(col1, col2, col3)
columnt上创建一个唯一约束来强制执行规则==&gt; S3和SX作为对可以属于多个columns1的值(但不超过column1的一个值)“一个例子:
CREATE TABLE T1_PAIRS (
Col2 varchar2(10), Col3 varchar2(10),
CONSTRAINT T1_PAIRS_PK PRIMARY KEY( col2, col3 ),
CONSTRAINT T1_col2_UQ UNIQUE( col2 )
);
INSERT ALL
INTO T1_PAIRS( col2, col3 ) VALUES( 'S', 'S2' )
INTO T1_PAIRS( col2, col3 ) VALUES( 'SX', 'S3' )
SELECT 1 FROM dual;
ALTER TABLE T1
ADD CONSTRAINT col2_col3_pair_fk
FOREIGN KEY ( col2, col3 ) REFERENCES T1_pairs( col2, col3 );
ALTER TABLE T1
ADD CONSTRAINT pair_can_belong_to_multi_col1 UNIQUE( col1, col2, col3 );