2012-04-17 16 views
10

Ho problemi con un indice Lucene, che ha parole indicizzate, che contengono caratteri "-".Problemi dell'indice Lucene con il carattere "-"

Funziona per alcune parole che contengono "-" ma non per tutti e non trovo il motivo, perché non funziona.

Il campo in cui sto cercando viene analizzato e contiene la versione della parola con e senza il carattere "-".

sto usando l'analizzatore: org.apache.lucene.analysis.standard.StandardAnalyzer

qui un esempio:

se cerco "gsx- *" ho ottenuto un risultato, il indicizzata campo contiene "SUZUKI GSX-R 1000 GSX-R1000 GSXR"

ma se cerco "v- *" non ho ottenuto alcun risultato. Il campo indicizzato del risultato atteso contiene: "SUZUKI DL 1000 V-Strom DL1000V-STROMVSTROM V STROM"

Se cerco "V-Strom" senza "*" funziona, ma se basta cercare " v-str "ad esempio non ottengo il risultato. (Ci dovrebbe essere un risultato perché è per una ricerca dal vivo per un negozio web)

Quindi, qual è la differenza tra i 2 risultati attesi? perché funziona con "gsx- " ma non con "v-"?

+0

Interessante, lavoro con Solr e guido V-Strom 650 :) –

+1

Hai effettivamente controllato il contenuto del campo indicizzato o ti aspetti che sia così? Se non usi il più grande strumento di indice Lucene di sempre - Luca: http://code.google.com/p/luke/ –

+0

sì, visualizzo lo stesso campo che sto cercando in – Zteve

risposta

12

StandardAnalyzer tratterà il trattino come spazio bianco, credo. Quindi trasforma la tua query "gsx-*" in "gsx*" e "v-*" in niente perché elimina anche i token a lettera singola. Quello che vedi come contenuto del campo nel risultato della ricerca è il valore memorizzato del campo, che è completamente indipendente dai termini che sono stati indicizzati per quel campo.

Quindi quello che vuoi è che "v-strom" nel suo complesso sia un termine indicizzato. StandardAnalyzer non è adatto a questo tipo di testo. Forse provate con lo WhitespaceAnalyzer o con lo SimpleAnalyzer. Se ancora non lo fai, hai anche la possibilità di mettere insieme il tuo analizzatore, o semplicemente iniziare quei due a mentare e comporli con ulteriori TokenFilters. Un'ottima spiegazione è data in the Lucene Analysis package Javadoc.

BTW non è necessario inserire tutte le varianti dell'indice, come V-strom, V-Strom, ecc. L'idea è che lo stesso analizzatore normalizzi tutte queste varianti al stessa stringa sia nell'indice che durante l'analisi della query.

+0

Grazie per il tuo aiuto, so che il display il valore è indipendente dal campo cercato/indicizzato, ma per il test ho visualizzato il campo in cui sto cercando. Uso anche luke per testare e analizzare il problema. Quindi quello di cui ho esattamente bisogno è che il cliente possa digitare v- e ottenga tutti i risultati che iniziano con v-. Cosa devo cambiare, che funzioni? Ho solo bisogno della sintassi giusta in modo da poter cambiare la query del cliente – Zteve

+0

Sono un po 'arrugginito con Solr, ma vorrei iniziare aggiungendo un campo aggiuntivo al tuo schema (ad esempio product_name) che dovresti solo minuscolo (campo type = in lettere minuscole). Aggiungi questo campo (OR) agli url della tua richiesta di ricerca come parametro aggiuntivo con peso maggiore. –

+0

quale tipo di sintassi/valore dovrebbe essere in questo campo nome_prodotto? lo stesso contenuto del campo indicizzato effettivo? È anche possibile modificare il valore del campo indicizzato, poiché potrei cambiarlo, ad esempio, in "V-STROM v-strom vstrom v strom V STROM", potrebbe una variazione del valore offrire la soluzione?L'unica cosa fissa è che il cliente dovrebbe essere in grado di trovare il risultato quando digita "v-str" o "v-" ecc. Nel campo di ricerca. – Zteve

3

ClassicAnalyzer gestisce '-' come carattere utile, non delimitatore. Come ho capito ClassicAnalyzer, gestisce '-' come il pre-3.1 StandardAnalyzer perché ClassicAnalyzer utilizza ClassicTokenizer che tratta i numeri con un '-' incorporato come codice prodotto, quindi il tutto viene tokenizzato come un unico termine.

Quando ero a Regenstrief ho notato questo dopo l'aggiornamento Luca, in quanto i termini medici standard di LOINC (LOINC è stato avviato da RI) sono identificati da un numero seguito da un '-' e una cifra di controllo, come il '1-8 "o" 2857-1 ". Le mie ricerche di LOINC come "45963-6" non hanno funzionato con StandardAnalyzer in Luke 3.5.0, ma sono riuscite con ClassicAnalyzer (e questo perché abbiamo creato l'indice con il 2.9.2 Lucene.NET).

+0

Ho appena provato e da Lucene 4.0.0 WhitespaceAnalyzer non rimuoverà il trattino, ma lo standard e il classico lo faranno. –

1

ClassicAnalzer è consigliato per indicizzare il testo contenente codici prodotto come "GSX-R1000". Lo riconoscerà come un singolo termine e non dividerà le sue parti.Ad esempio, il testo "Europa/Berlino" sarà suddiviso da ClassicAnalzer nelle parole "Europa" e "Berlino". Questo significa che se avete un testo indicizzato dal ClassicAnalyzer contenente la frase

Europe/Berlin GSX-R1000 

è possibile cercare "Europa", "Berlino" o "GSX-R1000".

Ma attenzione con quale analizzatore si utilizza per la ricerca. Penso che la scelta migliore per cercare un indice di Lucene sia KeywordAnalyzer. Con la KeywordAnalyzer è anche possibile cercare per i campi specifici in un documento e si può costruire query complesse come:

(processid:4711) (berlin) 

Questa query documenti di ricerca con la frase 'Berlin', ma anche un campo 'ProcessId' contenente il numero 4711

Ma se cerchi l'indice per la frase "europa/berlin" non otterrai alcun risultato! Questo perché KeywordAnalyzer non ha modificato la frase di ricerca, ma la frase "Europa/Berlino" è stata suddivisa in due parole separate da ClassicAnalyzer. Ciò significa che devi cercare separatamente "europe" e "berlin".

Per risolvere questo conflitto è possibile tradurre un termine di ricerca, immesso dall'utente, in una query di ricerca adatta alle vostre esigenze utilizzando il seguente codice:

QueryParser parser = new QueryParser("content", new ClassicAnalyzer()); 
Query result = parser.parse(searchTerm); 
searchTerm = result.toString("content"); 

Questo codice sarà tradurre il pharse serach

Europe/Berlin 

in

europe berlin 

che si tradurrà nel set di documenti previsto .

Nota: Questo funzionerà anche per situazioni più complesse. Il termine di ricerca

Europe/Berlin GSX-R1000 

sarà tradotto in:

(europe berlin) GSX-R1000 

che cercherà correttamente per tutte le frasi in combinazione con il KeyWordAnalyzer.