I have 4 tables
table item_values
(item_key, item_value)
table filter_model
(filter_key)
table item_includes
(include_key, filter_key_fk, item_key, include_value)
table item_excludes
(exclude_key, filter_key_fk, item_key, exclude_value)
I'd like to get all items from item_values for each filter_model that matches the includes and are not in the excludes
Query should be like
select item_values.item_key,
item_values.item_value,
filter_model.filter_key,
item_includes.include_value
from item_includes,
filter_model,
item_values
where filter_model.filter_key=item_includes.filter_key_fk
and item_values.item_value=item_includes.include_value
and not exists (select 'x'
from item_excludes
where item_excludes.filter_key_fk=filter_model.filter_key
and item_excludes.include_value=item_values.item_value);
this works fine but I need to create materialized views for fast refresh for performance purpose.
So the subquery forbids the fast_refresh.
select item_values.item_key,
item_values.item_value,
filter_model.filter_key,
item_excludes.exclude_value
from item_excludes,
filter_model,
item_values;
My idea was to vreate a MV for the exclusions (getting all excluded items) elligible for a fast refresh :
create materialized view mv_excluded
as
select item_values.item_key,
item_values.item_value,
filter_model.filter_key,
item_excludes.exclude_value
from item_excludes,
filter_model,
item_values
where filter_model.filter_key=item_excludes.filter_key_fk
and item_values.item_value=item_excludes.exclude_value;
and then create the main MV with the inclusions and removing rows in the mv_excluded.
How can I do this ?
There is a trick!
You can write not exists queries as an outer join, returning those rows where a (mandatory) column from the outer-joined table is null.
You can fast refresh these:
create table t1 (
c1 int primary key
);
create table t2 (
c1 int primary key
);
insert into t1 values ( 1 );
insert into t1 values ( 2 );
insert into t2 values ( 1 );
commit;
create materialized view log on t1 with rowid including new values;
create materialized view log on t2 with rowid including new values;
create materialized view mv
refresh fast on commit
as
select t1.rowid t1rid, t2.rowid t2rid, t1.*
from t1, t2
where t1.c1 = t2.c1 (+)
and t2.c1 is null;
select c1 from mv;
C1
2
insert into t2 values ( 2 );
commit;
select c1 from mv;
no rows selected
insert into t1 values ( 3 );
commit;
select c1 from mv;
C1
3