id | user_id | job_range | start_date | client_name| job_type | job_no | job_quan
1 | 4 | 1-3000 | 2014-05-13 | kenny's | coloured | t50000 | n4500
2 | 2 | 3001-4500 | 2014-05-13 | kenny's | coloured | t50000 | n4500
3 | 3 | 1-2000 | 2014-05-15 | fredy's | plain | t42100 | n5000
4 | 4 |2001-5000 | 2014-05-15 | fredy's | plain | t42100 | n5000
我想编写一个查询,该查询使用已输入数据库(job_range)的数字范围,并将其与job_no匹配,以避免其他用户将作业范围内的作业放入数据库。 数字不能在已经给出的较低范围内。对于任何特定作业,如果范围为1-2000,那么您无法在该作业的表中添加另一行,范围从1-2000开始,只能选择2001到5000之间的作业。所以用户只能选择做工作btw范围2001 -5000
答案 0 :(得分:2)
您必须制作专栏UNIQUE
。您可以通过运行此查询来执行此操作(您需要先删除重复的条目):
ALTER TABLE jobs ADD UNIQUE (desc)
然后,当您尝试运行查询并且desc列已经存在时,它将返回错误。
答案 1 :(得分:1)
CREATE TABLE test_dup (id number, dup_from number,dup_to number);
create table dup_val_range (range_values NUMBER);
ALTER TABLE dup_val_range
ADD CONSTRAINT rng_unique unique (range_values);
CREATE SEQUENCE rng_seq
INCREMENT BY 1
START WITH 1
MINVALUE 1
MAXVALUE 9999999999999999999
NOCYCLE
NOCACHE
NOORDER;
create or replace procedure ins_rng(p_from IN NUMBER, p_to IN NUMBER)
AS
v_indx1 NUMBER;
BEGIN
IF p_from> p_to THEN
RAISE_APPLICATION_ERROR(-20001, 'from is Higher tham To');
END IF;
-- check for nulls
FOR i IN p_from..p_to
LOOP
BEGIN
insert into dup_val_range (range_values)
values (i);
EXCEPTION WHEN DUP_VAL_ON_INDEX THEN
rollback;
RAISE_APPLICATION_ERROR(-20001, 'Range ir taken!');
END;
END LOOP;
insert into test_dup
values (rng_seq.nextval,p_from,p_to);
END;
exec ins_rng(p_from=>1, p_to=>19);
exec ins_rng(p_from=>5, p_to=>20);
ORA-20001: Range ir taken!
select * from dup_val_range
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
select * from test_dup
3 1 19
但是,如果不会通过此过程插入值,则会手动添加,这不会有帮助..
答案 2 :(得分:0)
正如Marcell所说,无法在INSERT上使用WHERE。
我倾向于根据你的表格布局和所需的动作在'desc'上设置一个UNIQUE键,然后执行标准的INSERT。如果已经插入了1-300,则INSERT将失败,并且您可以在应用程序中捕获重复键错误。
ALTER TABLE `jobs` ADD UNIQUE (desc);
答案 3 :(得分:0)
如果指定ON DUPLICATE KEY UPDATE,并且插入的行将导致UNIQUE索引或PRIMARY KEY中出现重复值,则执行旧行的UPDATE。例如,如果列a声明为UNIQUE并且包含值1,则以下两个语句具有相同的效果:
INSERT INTO table (a,b,c) VALUES (1,2,3) ON DUPLICATE KEY UPDATE c=c+1;
UPDATE table SET c=c+1 WHERE a=1;
以下是ON DUPLICATE KEY
http://dev.mysql.com/doc/refman/5.0/en/insert-on-duplicate.html
答案 4 :(得分:0)
你需要一种方法来拆分列(desc到desc_from和desc_to)或(substr string来获取from,to),你需要检查from不能大于to并且可以使用这样的东西.. < / p>
CREATE TABLE test_dup (id number, dup_from number,dup_to number);
select * from test_dup;
ALTER TABLE test_dup
ADD CONSTRAINT chk_dup CHECK (dup_from<=dup_to);
insert into test_dup
select 1,2,300 from dual where not exists (select 1 from test_dup where 2<=dup_to AND 300>=dup_from);
insert into test_dup
select 2,4,399 from dual where not exists (select 1 from test_dup where 4<=dup_to AND 399>=dup_from);
insert into test_dup
select 3,1,500 from dual where not exists (select 1 from test_dup where 1<=dup_to AND 500>=dup_from);
insert into test_dup
select 4,301,304 from dual where not exists (select 1 from test_dup where 301<=dup_to AND 304>=dup_from);
insert into test_dup
select 4,200,200 from dual where not exists (select 1 from test_dup where 200<=dup_to AND 200>=dup_from);
insert into test_dup
select 4,555,555 from dual where not exists (select 1 from test_dup where 555<=dup_to AND 555>=dup_from);
select * from test_dup;
1 2 300
4 301 304
4 555 555
其他?你可以使用基于函数的约束来进行相同的检查吗? 或者你可以创建一个新的检查表并添加唯一的约束。在插入实际表之前,如果有
,则将所有数据范围放入检查表中,以便在dupval上捕获错误insert into test_dup
select 1,2,300 from dual where not exists (select 1 from test_dup where 2<=dup_to AND 300>=dup_from AND dup_from<dup_to);
再来一次
create or replace procedure insert_rng (p_id IN NUMBER, p_from IN NUMBER, p_to IN NUMBER)
AS
BEGIN
insert into test_dup
select p_id,p_from,p_to from dual where not exists (select 1 from test_dup where p_from<=dup_to AND p_to>=dup_from AND dup_from<=dup_to);
IF sql%notfound THEN
RAISE_APPLICATION_ERROR(-20001, 'range taken!');
END IF;
END;
exec insert_rng (p_id=>1, p_from=>1, p_to=>99);
答案 5 :(得分:0)
如果您的INSERT
字段中的两个值的某些条件未得到满足,您希望desc
失败。
首先,正如user2879235所提到的那样,如果将desc
字段拆分为两个单独的列,则会更容易制定条件,让我们称之为start
和end
另一个问题是desc
中值的含义。有时你只有1个值,有时你有2个。
1000
只是1000-1000
的简写还是别的?我会假设它是。
并100-1000
和1000-1100
发生冲突或不发生冲突吗?我会假设他们这样做。
根据这些假设,我认为您的约束可以表述为(请验证这一点!)
NOT EXISTS (
SELECT j FROM jobs WHERE (j.start <= new.start AND j.end >= new.start)
OR (j.start <= new.end AND j.end >= new.end)
)
其中new
是新创建的元组。
您希望在尝试插入时检查此约束,但MySQL doesn't support checking CHECK constraints, so you'll need to use a trigger instead可以在满足此约束的相反时提升SIGNAL
,这应该回滚(即撤消) INSERT
。