Solr:字段值的完全匹配

时间:2014-11-23 10:49:14

标签: solr

我正在尝试对存储的值(而不是查询值)执行完全匹配。

我的索引数据类似于:“香蕉共和国”

我需要以下查询才能匹配:

  • 来自香蕉共和国的衬衫
  • 香蕉共和国项目
  • 东西香蕉共和国和其他东西

这些匹配:

  • 香蕉不共和
  • 香蕉是一种很好的水果
  • 智利共和国

使用类似于query_string LIKE '%stored_val%'的查询,我的方案实际上很简单,很容易使用SQL,但我无法配置anlayzers来执行它。我确信EdgeNGramFilter可以实现这一点,但创建长度超过30个字符的ngram将非常昂贵。

我当前的实施:在索引分析器中,使用solr.KeywordTokenizerFactory。在查询分析器中,使用solr.ShingleFilterFactory(2-4个令牌)。使用分析工具时,一切看起来都很好。但是使用查询API,查询将转换为:

rawquerystring: "match_name:"banana republic"",
parsedquery_toString: "match_name:"(banana bananarepublic) republic""

与我存储的令牌“bananarepublic”不匹配

我的分析链看起来像:

  <fieldType name="singletoken" class="solr.TextField">
    <analyzer type="index">
      <charFilter class="solr.MappingCharFilterFactory" mapping="../../common-config/mapping-ISOLatin1Accent.txt"/> <!-- map accented letters to their ascii equivilants -->
      <tokenizer class="solr.KeywordTokenizerFactory"/>
      <filter class="solr.LowerCaseFilterFactory" />
      <filter class="solr.PatternReplaceFilterFactory" pattern="[^A-Za-z0-9&amp; ]" replacement=" "/>
      <filter class="solr.PatternReplaceFilterFactory" pattern="(^\s+|\s+$)" replacement=""/> <!-- join everything in a single token with no spaces -->
    </analyzer>
    <analyzer type="query">
      <charFilter class="solr.MappingCharFilterFactory" mapping="../../common-config/mapping-ISOLatin1Accent.txt"/> <!-- map accented letters to their ascii equivilants -->
      <tokenizer class="solr.WhitespaceTokenizerFactory" />
      <filter class="solr.WordDelimiterFilterFactory" /> <!-- using all default options from: https://wiki.apache.org/solr/AnalyzersTokenizersTokenFilters#solr.WordDelimiterFilterFactory -->
      <filter class="solr.LowerCaseFilterFactory" />
      <filter class="solr.PatternReplaceFilterFactory" pattern="[^A-Za-z0-9&amp; ]" replacement=" "/>
      <filter class="solr.TrimFilterFactory" />
      <filter class="solr.ShingleFilterFactory" minShingleSize="2" maxShingleSize="4" outputUnigrams="true" tokenSeparator="" />
    </analyzer>
  </fieldType>

2 个答案:

答案 0 :(得分:0)

在4.x和trunk中,mm的默认值由q.op param决定(q.op = AND =&gt; mm = 100%; q.op = OR =&gt; mm = 0%)。请记住,默认运算符受schema.xml条目的影响。在旧版本的Solr中,默认值为100%(所有子句必须匹配)

您是否在查询中使用了这种语法?

your_domain替​​换:8983 / solr的/选择/ Q =香蕉+共和国&安培; DEFTYPE = dismax&安培; q.op = AND&安培; ...

OR

your_domain替​​换:8983 / solr的/选择/ Q =香蕉+共和国&安培; DEFTYPE = dismax&安培;毫米= 100%&安培; ...

答案 1 :(得分:0)

如果不诉诸自定义query Tokenizers,就无法解决此问题,因为问题在于标记化阶段。

假设我们有这句话:banana republic 我们想索引和查询这个确切的短语。 实际发生的是:

索引时间:当solr建立索引banana republic时,tokenizer会将此短语拆分为两个单独的短语,以便索引看起来像这样

短语:banana

短语:republic

查询时间: 在查询时,您还将搜索由OR操作加入的两个单独的短语。

你真正需要的是这样的东西:

索引:短语:banana republic作为一个标记。

查询:搜索词组:banana republic作为一个令牌。

最好的解决方案是使用is来使用像这样的自定义短语标记:https://github.com/lucidworks/auto-phrase-tokenfilter