2010-07-22 16 views
14

Il carattere jolly * può essere utilizzato solo alla fine di una parola, ad esempio user*.Come interrogare lucene con l'operatore "mi piace"?

Voglio interrogare con un modello simile a %user%, come farlo?

+0

problema Un po 'simile: [http://stackoverflow.com/questions/468279/lucene-net-leading-wildcard-character-throws-an-error](http:// stackoverflow.com/questions/468279/lucene-net-leading-wildcard-character-throws-an-error) – devson

risposta

9

Lucene fornisce il ReverseStringFilter che consente di eseguire la ricerca con caratteri jolly come utente *. Funziona indicizzando tutti i termini in ordine inverso.

Ma penso che non ci sia modo di fare qualcosa di simile a "LIKE% user%".

+2

Interessante. In effetti, significa che è necessario impostare anticipatamente il proprio indice per consentire i caratteri jolly iniziali. E guardando il bug (https://issues.apache.org/jira/browse/LUCENE-1398), sembra che tu possa solo specificare un carattere jolly iniziale, ma non uno finale nello stesso termine (perché allora tu sono tornati allo stesso problema). – Jon

6

Dal Lucene 2.1 è possibile utilizzare

QueryParser.setAllowLeadingWildcard(true); 

ma questo può uccidere le prestazioni. Il LuceneFAQ ha alcune informazioni in più per questo.

3

Quando ci pensate, non è del tutto sorprendente che il supporto di lucene per i caratteri jolly sia (normalmente) limitato a un carattere jolly alla fine di un pattern di parole.

I motori di ricerca per parole chiave funzionano creando un indice inverso di tutte le parole nel corpus, che viene ordinato in ordine di parola. Quando si esegue una ricerca normale senza caratteri jolly, il motore utilizza il fatto che le voci dell'indice sono ordinate per individuare la voce o le voci della parola in O(logN) passaggi in cui N è il numero di parole o voci. Per un pattern word con un carattere jolly suffisso, la stessa cosa accade per trovare la prima parola corrispondente, e altre corrispondenze vengono trovate scansionando le voci fino a quando la parte fissa del pattern non corrisponde più.

Tuttavia, per un modello di parola con un prefisso jolly e un suffisso wildcard, il motore avrebbe dovuto guardare tutti voci dell'indice. Questo sarebbe O(N) ... a meno che il motore non abbia costruito un'intera pila di indici secondari per corrispondere sottostringhe letterali di parole. (E questo renderebbe l'indicizzazione molto più costosa). E per schemi più complessi (ad es. Regex) il problema sarebbe ancora peggiore per il motore di ricerca.

14

Il problema con le query LIKE è che sono expensive in termini di tempo impiegato per l'esecuzione. È possibile impostare fino QueryParser per consentire che porta i caratteri jolly con il seguente:

QueryParser.setAllowLeadingWildcard(true)

e questo vi permetterà di fare ricerche come:

*user*

Ma questo ci vorrà molto tempo per l'esecuzione . A volte, quando le persone dicono di volere una query LIKE, ciò che in realtà vogliono è uno query. Ciò consentirebbe di eseguire la seguente ricerca:

user~

Che sarebbe abbinare i termini users e fuser. È possibile specificare una distanza di modifica tra il termine nella query e i termini che si desidera abbinare utilizzando un valore float compreso tra 0 e 1. Ad esempio, user~0.8 corrisponde a più termini di user~0.5.

Suggerisco inoltre di dare un'occhiata a regex query, che supporta la sintassi delle espressioni regolari per le ricerche di Lucene. Potrebbe essere più vicino a ciò di cui hai veramente bisogno.Forse qualcosa di simile:

.*user.*

Problemi correlati