-->

使用Lucene SpanQueries句子感知搜索(Sentence aware search w

2019-07-29 09:19发布

是否有可能使用Lucene的SpanQuery找到其中术语“红色”,“绿色”和“蓝色”都出现在单个句子中所有出现的?

我的第一个(不完整/不正确的)方法是编写放置一个特殊句式标记权标和句子在相同的位置,句子的第一个字和再查询类似下面的东西开始的分析:

SpanQuery termsInSentence = new SpanNearQuery(
  SpanQuery[] {
    new SpanTermQuery( new Term (MY_SPECIAL_SENTENCE_TOKEN)),
    new SpanTermQuery( new Term ("red")),
    new SpanTermQuery( new Term ("green")),
    new SpanTermQuery( new Term ("blue")),
  },
  999999999999,
  false
);

SpanQuery nextSentence = new SpanTermQuery( new Term (MY_SPECIAL_SENTENCE_TOKEN));

SpanNotQuery notInNextSentence = new SpanNotQuery(termsInSentence,nextSentence);

这个问题,当然,是nextSentence是不是真的一句,这是任何一句话标记,其中包括一个在这句话termsInSentence匹配。 因此,这是行不通的。

我的下一个方法是创建一个放置标记句子分析器前(即第一个字之前 ,而不是在相同的位置上的第一个字)。 这里的问题是,我当时必须考虑额外造成偏移MY_SPECIAL_SENTENCE_TOKEN 。 更重要的是,这将尤其是在第一个坏,当我用幼稚的图案拆分句子(例如,分上/\.\s+[A-Z0-9]/ ),因为我必须考虑到所有的当我搜索企业号航空母舰 (假)句子标记。

所以......我应该怎么处理这个?

Answer 1:

我将索引每个句子作为Lucene的文档,其中包括引号什么源文档的句子从来到现场。 根据您的源材料,句子/ LuceneDoc的开销可能接受的。



Answer 2:

实际上,看起来,你是相当接近的解决方案。 我认为索引结束句的标志是一个不错的办法。 问题是,你的结束句标志是你的SpanNearQuery ,这是什么是你扔了。 你问它找到一个跨度其中既包含和包含MY_SPECIAL_SENTENCE_TOKEN 。 查询自相矛盾,所以,当然,也不会找到任何匹配。 你真正需要知道的是,这三个条款(“红色”,“绿色”和“蓝色”)发生在跨度不重叠MY_SPECIAL_SENTENCE_TOKEN (即句子令牌不与那些出现在计算)。

此外,缺少的字段名的Term构建函数是问题,但Lucene的应该抛出一个异常抱怨这一点,所以猜测这里这不是真正的问题。 可能是因为Lucene的版本,在这被写没有抱怨SpanNears不匹配字段中的时间,因此,也许值得一提。

这似乎工作对我说:

SpanQuery termsInSentence = new SpanNearQuery(
    new SpanQuery[] {
        new SpanTermQuery( new Term ("text", "red")),
        new SpanTermQuery( new Term ("text", "green")),
        new SpanTermQuery( new Term ("text", "blue")),
    },
    9999, 
    false
);

SpanQuery nextSentence = new SpanTermQuery( new Term ("text", MY_SPECIAL_SENTENCE_TOKEN));

SpanQuery notInNextSentence = new SpanNotQuery(termsInSentence,nextSentence);

至于哪里拆分,而不是使用正则表达式的幼稚做法的句子,我会尝试使用java.text.Breakiterator 。 它并不完美,但它确实一个不错的工作。



文章来源: Sentence aware search with Lucene SpanQueries