【发布时间】:2020-07-11 13:36:52
【问题描述】:
我有这样的问题,这是我的数据结构
create table tab (
id_tab integer not null,
val1 integer,
val2 integer,
val3 integer,
val4 integer,
val5 integer,
val6 integer,
val7 integer,
val8 integer,
val9 integer,
CONSTRAINT tab_pk PRIMARY KEY (id_tab)
);
create index val1_index on tab (val1);
create index val2_index on tab (val2);
create index val3_index on tab (val3);
create index val4_index on tab (val4);
create index val5_index on tab (val5);
create index val6_index on tab (val6);
create index val7_index on tab (val7);
create index val8_index on tab (val8);
create index val9_index on tab (val9);
create procedure test1 as
begin
for x in 1..10000
loop
insert into tab(id_tab, val1, val2, val3, val4, val5, val6, val7, val8, val9)
values ((select nvl(max(id_tab), 0) + 1 from tab),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)),
decode(round(dbms_random.value(0,2)), 1, null, dbms_random.value(1,9)));
end loop;
end;
/
BEGIN
test1;
-- for my example, to find value:
insert into tab (id_tab, val1, val2, val3, val4, val5, val6, val7, val8, val9)
values(-1, 3, 1, null, 5, 2, 1, 9, null, 1);
END;
/
现在我正在寻找结果
SELECT * FROM tab
where
(decode(val1, 3, 1) = 1) and -- it's like: (val1 = 3 or (val1 is null and 3 is null)
(decode(val2, 1, 1) = 1) and
(decode(val3, null, 1) = 1) and -- it's like: (val1 = null or (val1 is null and null is null)
(decode(val4, 5, 1) = 1) and
(decode(val5, 2, 1) = 1) and
(decode(val6, 1, 1) = 1) and
(decode(val7, 9, 1) = 1) and
(decode(val8, null, 1) = 1) and
(decode(val9, 1, 1) = 1)
我有一个预期的结果:
问题是我有大约一百万个找到这样的组合,大约需要一个小时,问题是是否可以使用其他索引或以其他方式构造一个查询(在哪里)来搜索这样的组合省时吗?
这是一个例子: https://dbfiddle.uk/?rdbms=oracle_18&fiddle=ed77f058517197d4468e143f9deab3e1
数据库:Oracle 11 标准版一
【问题讨论】:
-
您可以尝试 FBIs(基于函数的索引),如果它们的参数是固定的,则每个
decode()s 一个。 -
我不明白。
decode(val1, 3, 1) = 1完全等价于val1 = 3,那你为什么要写得这么复杂——这也妨碍了在val1上使用索引?如果这不是您的实际查询 - 如果真正的查询更复杂,并且使用decode确实有某种目的 - 然后向我们展示真正的查询片段,而不是完全没有意义的模型。 -
3是输入参数,所以可以是NULL。 真正的问题是 - 谓词应该表现为NULL = NULL@mathguy -
decode(val1, :x, 1) = 1 当 val1 为 null 且 :x 为 null 然后 1 或 val1 = :x 然后 1. (decode(val1, :x, 1) = 1 ) = (val1 = :x or (val1 is null and x is null))
标签: oracle indexing where-clause