В чем разница между запросом фразы и использованием фильтра с галькой? - PullRequest
13 голосов
/ 21 декабря 2011

Я сейчас индексирую веб-страницу, используя lucene.Цель состоит в том, чтобы иметь возможность быстро извлечь, какая страница содержит определенное выражение (обычно 1, 2 или 3 слова) и какие другие слова (или группы из 1–3 из них) также находятся на странице.Это будет использоваться для создания / обогащения / изменения тезауруса (фиксированный словарь).

Из статей, которые я обнаружил, кажется, что проблема состоит в том, чтобы найти n-граммов (или гальку).

В Lucene есть ShingleFilter , ShingleMatrixFilter и ShingleAnalyzerWrapper , которые, похоже, связаны с этой задачей.

ОтВ этой презентации я узнал, что Lucene также может искать термины, разделенные фиксированным числом слов (называемых помоками).Вот пример здесь .

Однако я не понимаю четко разницу между этими подходами?Они принципиально отличаются или вам нужно сделать выбор размера / индекса?

В чем разница между ShingleMatrixFilter и ShingleFilter?

Надеюсь, гуру Люсена НАЙДЕТ этот вопрос,и так и ответь ;-)!

1 Ответ

17 голосов
/ 21 декабря 2011

Различия между использованием фразы и гальки в основном заключаются в производительности и выигрыше.

При использовании запросов фраз (скажем, «foo bar») в типичном случае, когда отдельные слова находятся в индексе, запросы фраз должны идти по инвертированному индексу для «foo» и «bar» и находить документы, которые содержат оба термины, а затем пройти их списки позиций в каждом из этих документов, чтобы найти места, где «foo» появился прямо перед «бар».

Это имеет определенную стоимость как для производительности, так и для оценки:

  1. Позиции (.prx) должны быть проиндексированы и найдены, это похоже на дополнительное «измерение» к инвертированному индексу, которое увеличит время индексации и поиска
  2. Поскольку в инвертированном индексе фигурируют только отдельные термины, реальная «фраза IDF» не вычисляется (это может не повлиять на вас). Так что вместо этого это приблизительно на основе суммы термина IDF.

С другой стороны, если вы используете опоясывающий лишай, вы также индексируете n-граммы слова, другими словами, если вы перелистываете до размера 2, у вас также будут такие термины, как "foo bar" в индексе. Это означает, что для данного запроса фразы он будет проанализирован как простой TermQuery, без использования каких-либо списков позиций. И поскольку теперь это «реальный термин», фраза IDF будет точной, потому что мы точно знаем, сколько документов существует этот «термин».

Но использование черепицы также имеет некоторые затраты:

  1. Увеличен размер словаря терминов, индекса терминов и размеров списков публикаций, хотя это может быть справедливым компромиссом, особенно если вы полностью отключите позиции с помощью Field.setIndexOptions.
  2. Некоторые дополнительные затраты на этапе анализа индексации: хотя ShingleFilter хорошо оптимизирован и довольно быстр.
  3. Нет очевидного способа вычисления «неаккуратных запросов фраз» или неточных совпадений фраз, хотя это может быть аппроксимировано, например, для фразы "foo bar baz" с черепицей размера 2 у вас будет два токена: foo_bar, bar_baz, и вы можете реализовать поиск с помощью некоторых других запросов lucene (например, BooleanQuery) для неточного приближения.

Как правило, индексирование словограмм такими вещами, как Shingles или CommonGrams, является всего лишь компромиссом (достаточно искусным) для снижения стоимости позиционных запросов или улучшения оценки фраз.

Но есть реальные варианты использования этого материала, хороший пример доступен здесь: http://www.hathitrust.org/blogs/large-scale-search/slow-queries-and-common-words-part-2

...