Oracle
 sql >> Database >  >> RDS >> Oracle

Oracle:ricerca full-text con condizione

Testo Oracle

1 - Puoi migliorare le prestazioni creando l'indice CONTEXT con FILTER BY:

create index my_idx on my_table(text) indextype is ctxsys.context filter by group_id;

Nei miei test il filter by decisamente migliorato le prestazioni, ma era ancora leggermente più veloce usare solo un indice btree su group_id.

2 - Gli indici CTXCAT utilizzano "sottoindici" e sembrano funzionare in modo simile a un indice a più colonne. Questa sembra essere l'opzione (4) che stai cercando:

begin
  ctx_ddl.create_index_set('my_table_index_set');
  ctx_ddl.add_index('my_table_index_set', 'group_id');
end;
/

create index my_idx2 on my_table(text) indextype is ctxsys.ctxcat
    parameters('index set my_table_index_set');

select * from my_table where catsearch(text, 'blah', 'group_id = 43') > 0

Questo è probabilmente l'approccio più veloce. L'utilizzo della query precedente su 120 MB di testo casuale simile allo scenario A e B richiedeva solo 18 risultati coerenti. Tuttavia, la creazione dell'indice CTXCAT ha richiesto quasi 11 minuti e ha utilizzato 1,8 GB di spazio.

(Nota:Oracle Text sembra funzionare correttamente qui, ma non ho familiarità con Text e non posso garantire che questo non sia un uso inappropriato di questi indici come ha detto @NullUserException.)

Indici a più colonne e join di indici

Per la situazione che descrivi nella tua modifica, normalmente non ci sarebbe una differenza significativa tra l'utilizzo di un indice su (A, B) e l'unione di indici separati su A e B. Ho creato alcuni test con dati simili a quelli che hai descritto e un join dell'indice richiedeva solo 7 get coerenti contro 2 get coerenti per l'indice a più colonne.

Il motivo è perché Oracle recupera i dati in blocchi. Un blocco è in genere 8K e un blocco di indice è già ordinato, quindi probabilmente puoi inserire i valori da 500 a 2000 in pochi blocchi. Se sei preoccupato per le prestazioni, di solito l'IO per leggere e scrivere blocchi è l'unica cosa che conta. Il fatto che Oracle debba o meno unire alcune migliaia di righe è una quantità irrilevante di tempo CPU.

Tuttavia, questo non si applica agli indici Oracle Text. Puoi unirti a un indice CONTEXT con un indice btree (una "bitmap e"?), ma le prestazioni sono scarse.