Lucene
Lucene — это библиотека с открытым исходным кодом, написанная на Java, которая позволяет индексировать и искать текст. Он используется в некоторых поисковых системах .
Это проект фонда Apache, доступный по лицензии Apache . Он также доступен для языков Ruby , Perl , C ++ , PHP , C # , Python .
Резюме
- 1 История
- 2 Как работает Lucene
- 2.1 Индексация
- 2.2 Исследования
- 3.1 Классы индексации
- 3.2 Исследовательские классы
- 4.1 Инструменты
- 4.2 Связанные проекты
- 4.2.1 Компоненты поисковой системы
- 6.1 Библиография
- 6.2 Статьи по теме
- 6.3 Внешние ссылки
Исторический
Lucene впервые загружен Дугом Каттингом на сайт SourceForge.net в Март 2000 г. . Затем он выпускается под Стандартной общественной лицензией ограниченного применения GNU . Его перевод в Apache Jakarta объявлен в Октябрь 2001 г. .
Проект Lucene взят из книги Lucene в действии (Lucene в действии), опубликованной в декабре 2004 года . Он написан совместно Эриком Хэтчером, одним из менеджеров проектов с открытым исходным кодом Ant , Lucene и Tapestry , и Отисом Господнетиком, активным участником проекта Apache Jakarta.
В 14 февраля 2005 г. , Lucene переходит на проект Apache Jakarta . База исходного кода конвертируется в контроллер версии SVN .
понедельник 12 декабря 2005 г. , Грант Ингерсол представляет на ApacheCon в США тематическое исследование Java по расширенному использованию компонентов Lucene, включая технические подробности обработки естественного языка .
Сегодня Lucene используется для поисковой системы очень большого количества продуктов и веб-сайтов по всему миру.
Как работает Lucene
Индексация
До взрыва Интернета , десятичная классификация Дьюи была очень эффективна при категоризации объектов в библиотеке. Однако в Интернете масса доступных данных стала настолько огромной, что теперь необходимо использовать альтернативные и более динамичные средства для поиска информации.
В основе всех поисковых систем лежит автоматический механизм индексации : однократная обработка необработанных данных и предоставление им нескольких высокоэффективных ссылок ускоряет поисковую операцию. Эта концепция очень похожа на указатель терминологии, который обычно находится в конце книги, что позволяет быстро находить страницы, посвященные заданной теме.
Если вам нужно охватить большое поле файлов или найти определенную строку символов в одном файле, вам не следует сканировать каждый файл последовательно для данной фразы. Потому что чем больше файлов, тем больше времени требуется на поиск информации . Лучше установить текстовый указатель в формате, позволяющем производить быстрый поиск, избегая последовательного метода. Этот процесс называется индексацией .
Исследовать
Исследование является действием поиска слов в индексе , чтобы найти ссылки на документы , когда они появляются. Качество поиска оценивается по позиционированию и релевантности результатов. Однако есть и другие факторы, влияющие на поиск. Скорость является определяющим фактором при обработке большого количества информации. Точно так же возможность поддержки простых или сложных запросов, опрос предложений, символов, позиционирования и сортировки результатов так же важны, как и простой в освоении синтаксис для ввода этих запросов.
Классы
В следующих разделах дается краткое введение в основные классы , которые используются для создания этой поисковой системы.
Классы индексации
- IndexWriter — класс IndexWriter является центральным компонентом процесса индексирования. Этот класс создает новый индекс и добавляет документы к существующему индексу. Мы можем думать об этом как об объекте, с помощью которого мы можем писать в индекс, но который не позволяет его читать или искать.
- Directory — класс Directory представляет расположение индекса Lucene. IndexWriter использует одну из реализаций каталога , FSDirectory , для создания своего индекса в каталоге в файловой системе . Другая реализация, RAMDirectory , хранит все свои данные в памяти. Это может быть полезно для небольших индексов, которые могут быть полностью загружены в память и могут быть уничтожены при завершении приложения.
- Анализатор — прежде чем текст попадет в индекс, он проходит через Анализатор. Это абстрактный класс, который используется для извлечения важных слов для индекса и удаления остальных. Этот класс является важной частью Lucene и может использоваться не только для входного фильтра.
- Document — класс Document представляет собой набор полей. Поля в документе представляют документ или метаданные, связанные с этим документом. Исходный источник (например, записи из базы данных, документ Word, глава из книги и т. Д.) Не имеет отношения к Lucene. Метаданные, такие как автор, заголовок, тема, дата и т. Д. индексируются и хранятся отдельно как поля в документе.
- Поле — каждый документ представляет собой индекс, содержащий одно или несколько полей, вставленных в класс под названием « Поле» . Каждое поле ( поле ) — это часть данных, которая запрашивается или извлекается из индекса во время поиска.
Исследовательские классы
- IndexSearcher — класс IndexSearcher предназначен для поиска того, что IndexWriter индексирует. Мы можем думать об этом как о классе, который открывает индекс в режиме только для чтения.
- Термин — термин — это основная единица поиска, аналогичная объектуполя . Это строка символов: имя поля и его значение. Обратите внимание, что используемые термины также включаются в процесс индексации.
- Query. Класс Query — это абстрактный класс, который включает в себя BooleanQuery , PhraseQuery , PrefixQuery , PhrasePrefixQuery , RangeQuery , FilteredQuery и SpanQuery .
- TermQuery — это самый простой метод запросов Lucene. Он используется для выравнивания документов, содержащих поля с определенными значениями.
- QueryParser — класс QueryParser используется для создания аналитического декомпозитора, который может выполнять поиск по индексу.
- Hits — Класс Hits представляет собой простой контейнер индекса для ранжирования результатов поиска для документов, которые появляются по заданному запросу. По соображениям производительности в примерах ранжирования из индекса загружаются не все документы для данного запроса, а только некоторые из них.
Ресурсы
Инструменты
- Luke (Lucene Index Toolbox) — это удобный инструмент диагностики и разработки, который обращается к существующим индексам Lucene и позволяет отображать и редактировать их содержимое различными способами. На Люка распространяется лицензия Apache, за исключением части кода.
- LIMO (Lucene Index Monitor) предоставляет основную информацию об индексах, используемых поисковой системой Lucene. Это проект SourceForge.
Связанные проекты
Все эти проекты являются или были подпроектами Apache Lucene и позволяют реализовать поисковую систему.
Компоненты поисковой системы
- Apache Solr : поисковый сервер на базе Lucene.
- Apache Nutch : индексирующий робот.
- Apache Hadoop : распределенная файловая система ( HDFS ) и распределенные вычисления с использованием парадигмы MapReduce .
- Apache Tika : библиотека извлечения данных и метаданных для самых разных форматов файлов.
- Elasticsearch : сервер для индексации и поиска данных
Примечания и ссылки
- ↑» LuceneTM Core News «(по состоянию на 3 декабря 2020 г. )
- ↑ Страница Lucene на SourceForge
- ↑Сессия, представленная на ApacheCon
- ↑ (in) Список приложений, использующих Lucene
Приложения
Библиография
- « Введение в Apache Lucene: создание полнотекстовых поисковых систем с открытым исходным кодом для Java », автор — Коши Секигути; Gijutsu-Hyohron Co, Ltd; ( ISBN4774127809 )
- « Лучена в действии » Эрика Хэтчера и Отиса Господнетича; Публикации Мэннинга; декабрь 2004 г. ; ( ISBN1932394281 ) (en) [1]
- Манфред Хардт, д-р Фабиан Тайс: » Сучмашины энтвикельн с апачем Люценом «; Программное обеспечение и поддержка Verlag, Франкфурт-на-Майне, Германия; Сентябрь 2004 г. ; ( ISBN3935042450 )
Статьи по Теме
Внешние ссылки
- (ru) Официальный сайт
- (ru) Wiki Lucene
Материал по работе с Apache Lucene и созданию простейшего нечёткого поиска

Пост расcчитан на начинающих, на людей незнакомых с технологией Apache Lucene. В нем нет материала о том, как устроен Apache Lucene внутри, какие алгоритмы, структуры данных и методы использовались для создания фреймворка. Пост является обучающим материалом-тизером, написанным для того, чтобы показать, как организовать простейший нечёткий поиск по тексту.
В качестве материала для обучения предоставлен код на github, сам пост в качестве документации и немного данных для тестирования поисковых запросов.
Введение
Подробно о библиотеке Apache Lucene написано здесь и здесь. В статье будут встречаться такие термины как: запрос, индексация, анализатор, нечеткие совпадения, токены, документы. Советую сначала прочитать вот эту статью. В ней эти термины описывают в контексте фреймворка Elasticsearch, который базируется на библиотеках Apache Lucene. Поэтому базовая терминология и определения совпадают.
Инструментарий
В статье описывается использование Apache Lucene 5.4.1. Исходный код доступен на github, в репозитории есть небольшой набор данных для тестирования. По сути статья является подробной документацией к коду в репозитории. Начать «играть» с проектом можно с запуска тестов в классе BasicSearchExamplesTest.
Создание индексов
Проиндексировать документы можно с помощью класса MessageIndexer. В нём есть метод index:
public void index(final Boolean create, List documents) throws IOException
Он принимает на вход переменную create и documents. Переменная create отвечает за поведение индексатора. Если она равна true, то индексатор будет создавать новый индекс даже если индекс уже существовал. Если false, то индекс будет обновляться.
Переменная documents это список объектов Document. Document это объект индексации и поиска. Он представляет собой набор полей, каждое поле имеет имя и текстовое значение. Для того чтобы получить список документов создан класс MessageToDocument. Его задача создавать Document используя два строковых поля: body и title.public static Document createWith(final String titleStr, final String bodyStr) < final Document document = new Document(); final FieldType textIndexedType = new FieldType(); textIndexedType.setStored(true); textIndexedType.setIndexOptions(IndexOptions.DOCS); textIndexedType.setTokenized(true); //index title Field title = new Field("title", titleStr, textIndexedType); //index body Field body = new Field("body", bodyStr, textIndexedType); document.add(title); document.add(body); return document; >Обратите внимание что метод index по умолчанию использует RussianAnalyzer, доступный в библиотеке lucene-analyzers-common.
Для того чтобы поиграть с созданием индекса перейдите к классу MessageIndexerTest.
Поиск
Для демонстрации базовых возможностей поиска создан класс BasicSearchExamples. В нём реализованы два метода поиска: простой поиск по токенам и нечеткий поиск. За простой поиск отвечают методы searchIndexWithTermQuery() и searchInBody(), за нечеткий поиск метод fuzzySearch().
В Lucene существует много способов создать запрос, но для простоты методы обычного поиска реализованы только с помощью классов QueryParser и TermQuery. Методы нечеткого поиска используют FuzzyQuery, которая зависит от одного важного параметра: maxEdits. Этот параметр отвечает за нечеткость поиска, подробности здесь. Грубо говоря, чем он больше, тем более расплывчатым/нечетким будет поиск. Погрузиться в многообразие способов сделать запрос можно здесь.
Для того чтобы поиграть с поиском перейдите к классу BasicSearchExamplesTest
Задание
Чтобы играть с проектом было не скучно попробуйте выполнить несколько заданий:
- Сделайте интерактивный консольный поиск. Поиск должен показывать выдачу и спрашивать следующий запрос.
- Сейчас поиск работает только с полем body. Сделайте так, чтобы поиск работал по полям title и body одновременно.
- Подсчитайте количество проиндексированных слов (токенов)
- Расширьте модель Message, добавьте в неё регион (region) и дату создания сообщения (creationDate). Не забудьте добавить новые поля для индексации в классе MessageToDocument. Добавьте новые способы поиска с фильтром по региону и дате
- Посмотрите на класс запросов MoreLikeThisQuery. Попробуйте сгруппировать все документы по похожести используя значение score.
- Скачайте вот этот файл, в нем около 5000 различных сообщений. Проверьте как работает группировка, новые запросы и фильтры.
Заключение
Преимущество Apache Lucene в его простоте, высокой скорости работы и низких требованиях к ресурсам. Недостаток в отсутствии хорошей документации, особенно на русском языке. Проект очень быстро развивается, поэтому книги, туториалы и Q/A, которыми забит интернет, давно потеряли актуальность. К примеру, у меня ушло 4-5 дней только на то, чтобы понять, как вытащить векторную модель TF-IDF из индексов Lucene. Надеюсь что этот пост привлечет внимание специалистов к этой проблеме недостатка информации.
Для тех же кто хочет погрузиться в мир Apache Lucene советую взглянуть на документацию Elasticsearch. Многие вещи там очень хорошо описаны, со ссылками на авторитетные источники и с примерами.
Оффтоп
Это мой первый более или менее серьезный пост. Поэтому прошу высказывать критику, отзывы и предложения. Я мог бы написать еще несколько статей, так как сейчас вплотную работаю с Apache Lucene.
Pavel Belousov’s Blog
О Lucene я слышал уже давно, но попробовать данную библиотеку как-то не удавалось. На этой неделе я всё-таки решил поисследовать ее. Начал с простых примеров, а дальше, возможно, заиспользую Lucene в проекте на работе. Чтобы самому более подробно разобраться с данной библиотекой, решил написать о ней несколько статей. В данной статье хочу рассказать про основы работы с Lucene, а именно: про построение индекса и про поиск документов.
Что такое Lucene?
The Apache Lucene — это свободная библиотека для высокоскоростного полнотекстового поиска, написанная на Java. Lucene портированна на многие популярные языки программирования, в том числе и на .NET.
Основные особенности данной библиотеки:- высокоскоростная индексация;
- мощный, точный и эффективный поисковый алгоритм.
Если вам необходимо встроить возможности Full-Text Search’а в ваше .NET-приложение, то Lucene.NET отличный кандидат. При помощи Lucene можно построить такую систему поиска, которая будет удовлетворять любым вашим требованиям. Lucene может использоваться для индексирования практически любого типа контента. Важно понимать, что созданный данные, по которым строится индекс могут меняться, поэтому необходимо постоянно обновлять используемый индекс.
Что нужно для работы с Lucene.NET?
Все исходники Lucene.NET открыты и находятся в SVN-репозитории. Соответственно их можно скачать, собрать и использовать полученную dll. Уже собранную библиотеку на официальном сайте скачать не получится, но можно ее взять из любого Open Source проекта, использующего Lucene.NET, например, Subtext (но там может оказаться не последняя версия).
UPDATE: На момент написания статьи выложенных бинарников не было, но теперь их выложили здесь. И обновился сам сайт проекта.
Построение индекса
После добавления Lucene.NET в референсы вашего проекта, необходимо создать индекс. Обычно он хранится в файлах, но для увеличения производительности его можно записывать в память.
Следующий код добавляет в индекс 1000000 документов:- Analyzer analyzer = new StandardAnalyzer();
- IndexWriter writer = new IndexWriter( «tmp» , analyzer);
- for (int i = 0; i < 1000000; i++)
- Document doc = new Document();
- doc.Add(
- new Field(
- «id» ,
- i.ToString(),
- Field.Store.YES,
- Field.Index.NO));
- doc.Add(
- new Field(
- «text» ,
- string .Format( » string.» , i),
- Field.Store.YES,
- Field.Index.TOKENIZED));
- writer.AddDocument(doc);
- if (i % 100000 == 0)
- Console.WriteLine(
- «[]: documents are saved.» ,
- i,
- DateTime.Now);
- >
- writer.Optimize();
- writer.Close();
* This source code was highlighted with Source Code Highlighter .
Первые 2 строки создают Writer, который и будет производить запись в индекс в папку tmp.
В цикле создается документ и в него добавляются несколько полей. Для каждого из полей можно настроить будет оно сохраняться/индексироваться или нет. Таким образом, в данном примере по полю text создается индекс, а по id — нет и оба поля хранятся в индексе.
Вызов метода Optimize уменьшит объем созданных файлов, но он может занять некоторое время, и это надо учитывать при построении высоконагруженных систем.
На моем ноутбуке 100000 таких документов сохраняется за 1-2 секунды, что мне кажется хорошей производительностью, хотя есть идеи в будущем поплотней потестировать производительность Lucene.NET.
Построение запросов
Для того, чтобы найти документы, достаточно написать следующий код:
- Analyzer analyzer = new StandardAnalyzer();
- QueryParser parser = new QueryParser( «text» , analyzer);
- Query query = parser.Parse( «string» );
- IndexSearcher searcher = new IndexSearcher( «tmp» );
- Hits hits = searcher.Search(query);
- int results = hits.Length();
- Console.WriteLine( «Found results» , results);
- for (int i = 0; i < results; i++)
- Document doc = hits.Doc(i);
- Console.WriteLine( «ID: » , doc. Get ( «id» ));
- Console.WriteLine( «Text found: » , doc. Get ( «text» ));
- >
- searcher.Close();
* This source code was highlighted with Source Code Highlighter .
Т.е. мы создаем запрос, выполняем поиск и проходимся по всем документам удовлетворяющим запросу.
Запрос можно создать несколько иначе:
Query query = new TermQuery( new Term( «text» , «string» ));
Что дальше?
Все вышеописанное — это простейший пример создания индекса и поиска по нему. В следующей статье я постараюсь описать основные элементы, которые используются в Lucene.NET.
Ссылки
- Getting started with Lucene.NET
- Lucene.NET Your first application
- How to get started with Lucene.NET
- Lucene tutorial
Введение в Lucene
В этом курсе вы познакомитесь с Lucene. Вы поймете, почему такая библиотека важна, а затем узнаете, как работает поиск в Lucene. Кроме того, вы узнаете, как интегрировать Lucene Search в ваши собственные приложения, чтобы обеспечить надежные возможности поиска. Проверьте это здесь !
Содержание
1. Введение
В этом курсе мы собираемся погрузиться в Apache Lucene. Lucene — это полнофункциональный полнотекстовый поиск с открытым исходным кодом Это означает, что Lucene поможет вам реализовать механизм полнотекстового поиска, адаптированный к потребностям ваших приложений. Мы собираемся разобраться с Java-вкусом Lucene, но имейте в виду, что существуют API-клиенты для различных языков программирования.
1.1 Что такое полнотекстовый поиск
Пользователи часто хотят получить список документов или источников, которые соответствуют определенным критериям. Например, пользователь библиотеки должен быть в состоянии найти все книги, написанные конкретным автором. Или все книги, в названии которых есть определенное слово или фраза. Или все книги, опубликованные в определенный год от конкретного издателя. Вышеуказанные запросы могут быть легко обработаны хорошо известной реляционной базой данных. Если у вас есть таблица, в которой хранятся кортежи (название, автор, издатель, год публикации) , вышеуказанные поиски могут быть эффективно выполнены. Теперь, что если пользователь захочет получить все документы, которые содержат определенное слово или фразу в их фактическом содержании? Если вы попытаетесь использовать традиционную базу данных и сохранить необработанное содержимое всех документов в поле кортежа, поиск займет недопустимо много времени.
Это связано с тем, что при полнотекстовом поиске поисковая система должна сканировать все слова текстового документа или текстового потока в целом и пытаться сопоставить с ним несколько критериев, например, найти определенные слова или фразы в его содержании. Подобные запросы в классической реляционной базе данных были бы безнадежными. Конечно, многие системы баз данных, такие как MySQL и PostgreSQL, поддерживают полнотекстовый поиск, как нативный, так и с использованием внешних библиотек. Но это не эффективно, не достаточно быстро и не настраивается. Но самая большая проблема — это масштабируемость. Они просто не могут обработать объем данных, который могут обработчики полнотекстового поиска.
1.2 Зачем нам нужны полнотекстовые поисковые системы
Процесс генерирования огромных объемов данных является одной из определяющих характеристик нашего времени и главным следствием технологических достижений. Это идет термином информационной перегрузки . При этом сбор и хранение всех этих данных полезны только в том случае, если вы можете извлечь из них полезную информацию, а также сделать их доступными для конечных пользователей вашего приложения. Самым известным и используемым инструментом для достижения этой цели является, конечно же, поиск.
Можно утверждать, что поиск файлов по слову или фразе так же прост, как и последовательное сканирование сверху вниз, как если бы вы использовали команду grep . На самом деле этого может быть достаточно для небольшого количества документов. Но как насчет огромных файловых систем с миллионами файлов, и если это кажется вам необычным, как насчет веб-страниц, баз данных, электронных писем, репозиториев кода, и это лишь некоторые из них, и как насчет всех их вместе взятых. Становится легко понять, что информация, в которой нуждается каждый отдельный пользователь, может находиться в небольшом документе, где-то в огромном океане различных информационных ресурсов. И поиск этого документа должен казаться таким же легким, как дыхание.
Теперь можно понять, почему полностью настроенные приложения, основанные на поиске, привлекают много внимания и внимания. В дополнение к этому, тот факт, что поиск стал настолько важным аспектом работы конечного пользователя, что для современных веб-приложений, начиная от простых блогов и заканчивая большими платформами, такими как Twitter или Facebook и даже приложениями военного уровня, непостижимо, если у них нет средств поиска. И именно поэтому крупные поставщики не хотят рисковать путаницей в своих функциях поиска и хотят сделать их максимально быстрыми и в то же время максимально простыми. Это привело к необходимости обновить поиск с простой функции до полной платформы. Платформа, обладающая мощью, эффективностью, необходимой гибкостью и индивидуальной настройкой. А Apache Lucene обеспечивает, поэтому используется в большинстве вышеупомянутых приложений.
1.3 Как работает Lucene
Итак, вам должно быть интересно, как Lucene может выполнять очень быстрый полнотекстовый поиск. Не удивительно, что ответ заключается в том, что он использует индекс . Индексы Lucene попадают в категорию инвертированных индексов . Вместо классического индекса, где для каждого документа у вас есть полный список слов (или терминов ), которые он содержит, инвертированные индексы делают это наоборот. Для каждого термина (слова) в документах у вас есть список всех документов, которые содержат этот термин. Это намного удобнее при выполнении полнотекстового поиска.
Причину того, что инвертированные индексы работают так хорошо, можно увидеть на следующих диаграммах. Представьте, что у вас есть 3 очень больших документа. Классический указатель у вас в форме: