2010-03-29 8 views
7

He creado un índice con varios bits de datos para cada documento que he agregado, cada documento puede diferir en su nombre de campo.Lucene.NET y búsqueda en múltiples campos con valores específicos

Más tarde, cuando me vienen a buscar en el índice tengo que consultar con el terreno/valores exactos - por ejemplo:

FieldName1 = X AND FieldName2 = Y AND FieldName3 = Z 

¿Cuál es la mejor manera de construir la siguiente utilizando Lucene .NET:

  • ¿Qué analizador es mejor usar para este tipo de concordancia exacta?
  • Al recuperar una coincidencia, solo necesito que se devuelva un campo específico (que agrego a cada documento) - ¿debería ser el único almacenado?
  • Más adelante, tendré que admitir la búsqueda de palabras clave (por lo que un campo puede tener una lista de valores y tendré que hacer una coincidencia parcial).

Los campos y valores provienen de un Dictionary<string, string>. No es una entrada del usuario, está construida a partir de código.

Gracias,
Kieron

Respuesta

7

Bueno, lo he descubierto con el tiempo - aquí está mi opinión sobre ella (esto podría estar completamente equivocado, pero funciona para):

public Guid? Find (Dictionary<string, string> searchTerms) 
{ 
    if (searchTerms == null) 
     throw new ArgumentNullException ("searchTerms"); 

    try 
    { 
      var directory = FSDirectory.Open (new DirectoryInfo (IndexRoot)); 
      if (!IndexReader.IndexExists (directory)) 
       return null; 

      var mainQuery = new BooleanQuery(); 
      foreach (var pair in searchTerms) 
      { 
       var parser = new QueryParser (
        Lucene.Net.Util.Version.LUCENE_CURRENT, pair.Key, GetAnalyzer()); 
       var query = parser.Parse (pair.Value); 

       mainQuery.Add (query, BooleanClause.Occur.MUST); 
      } 

      var searcher = new IndexSearcher (directory, true); 

      try 
      { 
       var results = searcher.Search (mainQuery, (Filter)null, 10); 
       if (results.totalHits != 1) 
        return null; 

       return Guid.Parse (searcher.Doc (results.scoreDocs[0].doc).Get (ContentIdKey)); 
      } 
      catch 
      { 
       throw; 
      } 
      finally 
      { 
       if (searcher != null) 
        searcher.Close(); 
      } 
    } 
    catch 
    { 
      throw; 
    } 
} 
Cuestiones relacionadas