Подтвердить что ты не робот

Как выполнить сопоставление строк Java с помощью булевого синтаксиса поиска?

Я ищу библиотеку Java/ Scala, которая может принимать пользовательский запрос и текст и возвращает, если есть соответствие или нет.

Я обрабатываю поток информации, т.е. Twitter Stream, и не могу позволить использовать процесс пакетной обработки, мне нужно оценить каждый твит в реальном времени, вместо того, чтобы индексировать его через Lucene RAMDisk и запрашивать его позже.

Возможно создать парсер/лексер, используя ANTLR, но это такое обычное использование, что я не могу поверить, что никто не создает lib раньше.

Некоторые примеры из TextQuery Ruby library, который делает именно то, что мне нужно:

    TextQuery.new("'to be' OR NOT 'to_be'").match?("to be")   # => true

    TextQuery.new("-test").match?("some string of text")      # => true
    TextQuery.new("NOT test").match?("some string of text")   # => true

    TextQuery.new("a AND b").match?("b a")                    # => true
    TextQuery.new("a AND b").match?("a c")                    # => false

    q = TextQuery.new("a AND (b AND NOT (c OR d))")
    q.match?("d a b")                                         # => false
    q.match?("b")                                             # => false
    q.match?("a b cdefg")                                     # => true

    TextQuery.new("a~").match?("adf")                         # => true
    TextQuery.new("~a").match?("dfa")                         # => true
    TextQuery.new("~a~").match?("daf")                        # => true
    TextQuery.new("2~a~1").match?("edaf")                     # => true
    TextQuery.new("2~a~2").match?("edaf")                     # => false

    TextQuery.new("a", :ignorecase => true).match?("A b cD")  # => true

Как только он был реализован в Ruby, он не подходит для моей платформы, также я не могу использовать JRuby именно для этого момента в нашем решении:

Я нашел аналогичный вопрос, но не смог получить ответ от него: Boolean Query/Expression для дерева синтаксиса Concrete

Спасибо!

4b9b3361

Ответ 1

Учитывая, что вы выполняете текстовый поиск, я попытаюсь использовать некоторую инфраструктуру, предоставленную Lucene. Возможно, вы могли бы создать QueryParser и вызвать parse, чтобы вернуть Query. Моментальные подклассы Query:

TermQuery
MultiTermQuery
BooleanQuery
WildcardQuery
PhraseQuery
PrefixQuery
MultiPhraseQuery
FuzzyQuery
TermRangeQuery
NumericRangeQuery
SpanQuery

Затем вы можете использовать сопоставление шаблонов для реализации того, что означает соответствие для вашего приложения:

def match_?(tweet: String, query: Query): Boolean = query match {
  case q: TermQuery => tweet.contains(q.getTerm.text)
  case q: BooleanQuery => 
    // return true if all must clauses are satisfied
    // call match_? recursively
  // you need to cover all subclasses above
  case _ => false
}

val q = queryParser.parse(userQuery)
val res = match_?(tweet, q)

Вот реализация. У него наверняка есть ошибки, но вы получите эту идею, и это показывает действующее доказательство концепции. Он повторно использует синтаксис, документацию и грамматик по умолчанию Lucene QueryParser.

Ответ 2

Spring Язык выражения (SpEL) поддерживает оператор matches, который возвращает boolean на основе регулярных выражений. См. этот раздел документации для использования.

Это также позволит вам использовать логические операторы, такие как and, or и not.