Cli*_*ton 8 sql database oracle indexing
我有一个表有活动的非活动条目,活动= 1表示活动,活动= 0表示不活动.
我在这个表上有各种索引,但我只需要为活动条目维护索引,因为应用程序只查询活动数据.需要保留非活动数据,因为它可以再次变为活动状态,但这通常只能通过批量更新完成,无论如何都不会使用索引.
我注意到索引非活动条目(有越来越多的活动条目)占用相当多的空间.
Oracle(10g)中有没有办法做这样的事情:
create index an_idx on tab (active, col1, col2, ... , coln) where active = 1?
以前的尝试:
我尝试使用基于函数的索引将第一列设置为null,active = 0如下所示:
create index an_idx on tab (decode(active, 1, 1, null), col1, col2, ... , coln)
但在这种情况下,Oracle似乎仍然会为非活动列编制索引.
Dav*_*sta 12
您的基本想法是正确的,但您需要将解码应用于所有列.只有当所有索引表达式NULL都未对该行进行索引时.
create index an_idx on tab (
decode(active, 1, col1, null),
...
decode(active, 1, coln, null)
)
Run Code Online (Sandbox Code Playgroud)
当然,如果您希望查询使用此索引,则必须在WHERE子句中使用相同的表达式.
注意我不认为您希望decode(active, 1, 1, null)在索引中包含表达式,因为它对于所有索引行都是常量.
通过ACTIVE对表进行分区,创建本地索引,并使非活动分区的索引不可用.这将消除索引非活动数据所花费的时间.
create table tab(active number, col1 number, col2 number, col3 number)
partition by list(active)
(partition tab_active values(1), partition tab_inactive values(0));
create index tab_index1 on tab(col1) local;
alter index tab_index1 modify partition tab_inactive unusable;
Run Code Online (Sandbox Code Playgroud)
但这种方法有一些潜在的缺点:
在Oracle 12c中,您可以使用部分索引来完成此操作:
create table tab(active number, col1 number, col2 number, col3 number)
partition by list(active)
(partition tab_active values(1) indexing on,
partition tab_inactive values(0) indexing off);
create index tab_index1 on tab(col1) local indexing partial;
Run Code Online (Sandbox Code Playgroud)