LINUX.ORG.RU

Полнотекстовый поиск в PostgreSQL

 


1

0

Хотя тема поиска произвольного текста очень хорошо освещена в превосходной документации PostgreSQL, статья Пола Сефтона (Paul Sephton) "Полнотекстовый поиск в PostgreSQL" может служить введением для тех, кто планирует в дальнейшем глубже изучить эту тему.

>>> Подробности

★★★

Проверено: Shaman007 ()

переводная статья ... Где новость ?

SI ★★☆☆
()

Мдя, полнотекстовый поиск в постгресс хотя и рулит (по сравнению с проприетарными аналогами по скорости) - но ему ещё оказывается до люцины - как до китая раком... И пре-парсер на Yacc писать не надо, и анализаторы вполоть до эвристических поисков и фаззи и "LikeThis" поддерживается эффективно и булевский сёрч не в пример более разработанный (юседж как у гугла + возможности через АПИ) и много других фишек серьёзных поисковиков типа гугла, яху "из коробки". Здесь ещё работать и работать.. Не говоря о том что люцину встроить - кинуть файл менее мегабайта (в отличие от установки отдельного постгрес сервера с расходами на администрирование и прочее).

siberean
()
Ответ на: комментарий от siberean

интересно, можно ли в постгресс иметь прямой АПИйный доступ к стем/стоп словам (добавлять то-есть), нормам, токенайзеру (ах да, токенайзера тут нет), ну хотя бы твикать/переопределять анализаторы - под несуществующие языки. Если нет - то почему бы не взять разработчикам порт люцины (как движок, написанный специалистами в сёрче) и встроить в посгресс, имея тот-же код-бэйс?

siberean
()

модеры, а где моя новость про люцину и американских разведчиков?
Как кстати увидеть неподтверждённые новости?

siberean
()
Ответ на: комментарий от siberean

> интересно, можно ли в постгресс иметь прямой АПИйный доступ к стем/стоп словам (добавлять то-есть), нормам,

API словарей открыт, пишите свои словари

> токенайзеру (ах да, токенайзера тут нет),

Есть, оно парсер зовется. Парсеры подключаемые, японцы для своего языка сделали парсер. У них слова в тексте пробелами не разделяются :)

> ну хотя бы твикать/переопределять анализаторы - под несуществующие языки.

Сколько угодно

> Если нет - то почему бы не взять разработчикам порт люцины (как движок, написанный специалистами в сёрче) и встроить в посгресс, имея тот-же код-бэйс?

Возьми и сделай. Говорю тебе как "специалист в сёрче"

teodor
()
Ответ на: комментарий от siberean

Lucene все-таки про другое, вы внимательно почитайте. Если вам нужен просто поиск по помойке, то для этого постгрес вам не нужен. А вот если у вас есть база данных по структурированным данным и политикой доступа, плюс необходимость транзакционного обновления, то никакая Lucene вам не поможет. В крайнем случае, вы можете прикрутить Сфинкс, но и тут вы потеряете много.

Олег

megera
()
Ответ на: комментарий от siberean

> Не говоря о том что люцину встроить - кинуть файл менее мегабайта (в отличие от установки отдельного постгрес сервера с расходами на администрирование и прочее).

Lucene не решает задачи:

- поиск в базе со сложными метаданными

- ACID'ность при изменении данных в базе

teodor
()
Ответ на: комментарий от teodor

2 Олег и teodor:

ACID'ность уже есть, но да, нет гранулярности реляционок (лок по строкам, по таблицам, а не по всей базе). Дело в том - что люцина была создана как аналог гугловского энджина, где индекс создаётся по ночам батч-процессом. Или как минимум - инкрементальные райты очень редки и есть только один райтер в момент времени. (хотя можно как в мейнфрейме - выстраивать все транзакции в очередь - и посылать райт-транзакции туда и не иметь проблем с многими райтерами). Короче, есть транзакции в люцине, есть.

А что есть сложные метаданные (да знаю, я знаю, много лет работаю с реляционками)? Ведь людям надо делать поиск по всем полям - вне зависимости от того - как искуственно кто-то разбил всё по полям. Поля только мешают и я например наоборот все поля сливал в одно - для индексации. Я хочу сказать - что структурирование информации - ортогонально задаче поиска. В поиске наоборот - нужно "облако", особенно для всяких там фаззи и других умных сёрчей, с разными там весами.

siberean
()
Ответ на: комментарий от siberean

потом в люцине - есть поля. Я именно по полям и хожу и могу с разным весом засадить разные поля - любое их количество. Сильной стороной считаю реализацию супер-быстрого сёрча (чтения), и внутреннюю имплементацию - как многие токены внутри документа - маппятся на термы, ну и кучу парсеров и анализаторов, куда уже вложено масса интеллекта спецов по сёрчу. Повторить (я когда-то намеревался в молодости по наивности - думая о сёрче только как о частотах слов и булевской логике) - не имеет смысла. Там столько мелких деталей, взять те-же коэффициенты в полиномах определения веса, word distances коэффициенты итд (которые те спецы притащили из своих Excite, а создатель Люцины - когда-то создатель Excite). Да взять хотя-бы гораздо более примитивный алгоритм Бернштейна или беркли из 2 строчек:

while ((c = *str++)) hash = c + (hash << 6) + (hash << 16) - hash;

Поди, получи/найди - почему для английского языка там наиболее оптимальны именно 6 и 16? А сколько эвристики и колдовства в анализаторах - я могу себе представить...

Поэтому и полагаюсь на спецов - где они более компетентны, используя люцину.

siberean
()
Ответ на: комментарий от siberean

> ACID'ность уже есть, но да, нет гранулярности реляционок (лок по строкам, по таблицам, а не по всей базе).

Нет в смысле онлайновости: вставил запись и она сразу после коммита может быть найдена. Lucene сможет найти это только после своего batch-процессинга, а это не всегда приемлемо.

> А что есть сложные метаданные (да знаю, я знаю, много лет работаю с реляционками)? Ведь людям надо делать поиск по всем полям - вне зависимости от того - как искуственно кто-то разбил всё по полям.

Угу. Типа найди мне все документы, которые: - написаны таким автором (user_id) - написаны до 20.07.2005 - относяться к теме астрономия или ее подтеме - откомментированы пользователем таким-то (user_id-2) - содержат линки на такую статью - ну и наконец содержит слова "черная дыра"

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

teodor
()
Ответ на: комментарий от teodor

>Lucene сможет найти это только после своего batch-процессинга, а это не всегда приемлемо.

не-а, там есть коммит. Можно иметь много ридеров и когда райтер сделает коммит - ридеры сразу-же увидят. Онлайн.

Я пытался вытащить это неиспользуемую функциональность в проекте AIS: http://sourceforge.net/projects/ais/ сгрузите, там 2 мега всего. Можете проиндексировать весь диск (сделав его доступным добавлением линка из www или под виндой - замаппив диск под буквой, в виндовой терминологии я не силён, сорри), затем онлайн делайте "put" с одновременными "get". Ваши ассоциации, мемо/записки будут добавляться к существующей базе, созданной батчем.

> Угу. Типа найди мне все документы, которые: - написаны таким автором (user_id) - написаны до 20.07.2005 - относяться к теме астрономия или ее подтеме - откомментированы пользователем таким-то (user_id-2) - содержат линки

это всё можно. Я там начал было делать плугин инфраструктуру -для добавления форм со структурированной информацией (автор, титул, издательство, год итд). Не вижу большого отличия с тем - как я раньше использовал берклиДБ или реляционку.

siberean
()
Ответ на: комментарий от teodor

> Угу. Типа найди мне все документы, которые: - написаны таким автором (user_id) - написаны до 20.07.2005 - относяться к теме астрономия или ее подтеме - откомментированы пользователем таким-то (user_id-2) - содержат линки на такую статью - ну и наконец содержит слова "черная дыра"

Вы прямо на SQL-е разговариваете ;)

ну, для структурированной информации конечно удобна реляционка. Но мир движется к фаззи, к облакам терминов. Очень много ресёрча в данный момент. Например, вам надо сделать запрос на Обаму. Традиционно Вы будете искать на кейворд "Обама". И не получите документ имеющий в заглавии "43-й президент". Это конечно экстремальный случай, решения для которого сейчас ищется многими исследованиями. Но фаззи (ошибка в букве) - поддерживается уже сейчас и трандиционными способами "like %" это не решишь. Людей делающих поиск - не интересует конкретная имплементация - как программер структурировал документ. Это - артефакты, издержки хранения, нормализаций. Человека, делающего поиск - интересует моментальный релевантный возврат нужного ему результата, и всё.

siberean
()
Ответ на: комментарий от siberean

> не-а, там есть коммит. Можно иметь много ридеров и когда райтер сделает коммит - ридеры сразу-же увидят. Онлайн.

Ни согласен. Lucene - это поисковая система, а не база данных. Это внешняя по отношению к базе система полнотестового поиска и только.

Вставка документа в сложных системах может затрагивать десятки и сотни таблиц.

teodor
()
Ответ на: комментарий от siberean

я всё же попрошу модераторов (ау?) - дать мне линк на новость, которую я запостил, но её не утвердили (переписывать влом, и я потерял линк;)

Там я написал - что ЦРУ неделю назад или типа того - сделала стратегическое инвестирование в люцину. Это неспроста. Индесксирование тера/пета-байтных архивов и поиск с моментальным возвратом результата - возможно только люциной (имхо). Я так понимаю - что реальные базы данных - это как раз и есть - большие файлопомойки. Хитрые алгоритмы, эвристика (тех ресёрчей) - может хорошо идти в люциновские анализаторы и прочее. Как эффективно реализовать это на реляционке - я не представляю (класть блобы/клобы? не красибо и криво).

siberean
()
Ответ на: комментарий от siberean

> Вы прямо на SQL-е разговариваете ;)

:)

> ну, для структурированной информации конечно удобна реляционка.

Угу

> Но мир движется к фаззи, к облакам терминов

Угу-2, но оно не отменяет реляционик

> фаззи (ошибка в букве) - поддерживается уже сейчас и трандиционными способами "like %" это не решишь

contrib/pg_trgm создан как раз для таких корректировок и может жить с FTS

> Человека, делающего поиск - интересует моментальный релевантный возврат нужного ему результата, и всё.

Угу-3. Но к сожалению, релевантность - это то, что пользователь ожидал получить, а от разных систем он ожидает разного. Ни один Гугл не догадается, что я пытался вспомнить штат Алабама, а не найти номер его президентства.

В "их интрАнетах" (в смысле не-общепользовательских системах) очень часто эту облачность зарубают.

teodor
()
Ответ на: комментарий от siberean

> что реальные базы данных - это как раз и есть - большие файлопомойки.

И это бывает, но там не часто встречаются требования на ACID и online-индексацию.

> Индесксирование тера/пета-байтных архивов и поиск с моментальным возвратом результата - возможно только люциной (имхо)

Google-подобные машины, ориентированные на поиск самого релевантного, а не найти все и отрелевировать

> Как эффективно реализовать это на реляционке - я не представляю (класть блобы/клобы? не красибо и криво).

А никак :). Не про это они. Они для OLTP, а выше приведенное - OLAP

teodor
()
Ответ на: комментарий от teodor

> Ни согласен. Lucene - это поисковая система, а не база данных. Это внешняя по отношению к базе система полнотестового поиска и только.

это как её обычно используют. я пытаюсь использовать более полно.

Тогда что есть база данных? Что - иерархическая база данных - не база данных? А сетевая? Реляционками все заболели в 80-е и ещё долго будут пожинать плоды нормализации. А иерархические базы данных сохранились в виде файловых систем. Чем не база? Я могу нагреппать, наsed'ать то-же самое. Я знаю людей, могущих делать запросы через униксовые тулы к иерархическим базам - с не меньшей эффективностью чем возможно вы - делаете то-же через SQL. И представят результат в виде текстовых табличек тут-же.

> Вставка документа в сложных системах может затрагивать десятки и сотни таблиц.

Это проблемы конкретной реализации.

siberean
()
Ответ на: комментарий от teodor

ну так сёрч - это и есть область уж никак не реляционщиков. OLTP (и OLAP - в том случае - когда информация изначально структурировання, т.е. приходит из засабмиченных форм) - это временное хранение структур. Так сказать - персистент мемори, артефакт/издержки реализации.

Так же можно сохранять всё в файлах (на бекенде), класть в определённые директории, создавая CSV или fixed-length файлы на лету из форм. И сразу-же индексировать. Но слишком много лет вдалбливали реляционки - как единственно-возможный метод хранения структурированной информации - что пока никто не готов к этому. Кроме гуглов, некоторых телекомов (хранящих даже структурированную инфу в базах типа берклиДБ или LDAP), ОО баз. (нет, я за реляционки тоже, но - против отдачи сёрча им на растерзание. Это как оракел хотел всё встроить себе в базу - от апачи, JVM до сервера приложений. Комбайны обычно делают всё - плохо. Уних-вей - это отдельный сёрч енджин имхо).

(круто, написал про оракле и капча - redwood ;), однако...

siberean
()
Ответ на: комментарий от teodor

> Угу. Типа найди мне все документы, которые: - написаны таким автором (user_id) - написаны до 20.07.2005 - относяться к теме астрономия или ее подтеме - откомментированы пользователем таким-то (user_id-2) - содержат линки на такую статью - ну и наконец содержит слова "черная дыра"

Однако в постгрессе это все тоже работает довольно своеобразно - полнотекстовый индекс и индексы по целым/датам работают независимо. Постгресс делает два поиска -один по словам, а второй - по другим критериям, потом делает merge. В итоге это хорошо работает если обе половины запроса дают небольшое количество записей. Если нет (например как в поиске на lor) - запросы отрабатывают сильно долго и используют дамп данных на диск (т.к. work_mem не резиновый)

maxcom ★★★★★
()
Ответ на: комментарий от siberean

> я всё же попрошу модераторов (ау?) - дать мне линк на новость, которую я запостил, но её не утвердили (переписывать влом, и я потерял линк;)

не ной - ссылки на все твои топики есть в whois

maxcom ★★★★★
()
Ответ на: комментарий от siberean

гм, действительно. Надо будет сделать там их посмотр как-нибудь

maxcom ★★★★★
()
Ответ на: комментарий от maxcom

>Однако в постгрессе это все тоже работает довольно своеобразно - полнотекстовый индекс и индексы по целым/датам работают независимо

v svoyo vremya ya prikrytil GIN s kakimto patchem i polychil sostavnoi index po Date + Text'y :-) Davno eto bilo ... echo do vklycheniya v osnovnoe yadro postgresta, NO na opredelennyu Datu iskalo mychoi ! xot i po odnomy slovy nachodilo po 10k dokymentov :-)

kred
()
Ответ на: комментарий от maxcom

> Однако в постгрессе это все тоже работает довольно своеобразно - полнотекстовый индекс и индексы по целым/датам работают независимо.

Уже устарело :) В 8.4 появился многоколоночный GIN и contrib/btree_gin

teodor
()
Ответ на: комментарий от siberean

> Так же можно сохранять всё в файлах (на бекенде)...

Для любой заданной задачи можно написать более быстрое/эффективное хранилище чем реляционка. Вопрос времени и денег, реляционка обычно сильно дешевле и в разработке и в эксплуатации - умные люди уже позаботились и о надежности и о скорости.

Но все это справедливо, пока не предъявляются высокие требования по скорости и/или объемам. Тогда реляционки, в силу своего универсализма, начинают сливать специализированным или кастомным хранилищам.

> Комбайны обычно делают всё - плохо. Уних-вей - это отдельный сёрч енджин имхо).

Они делают все, но каждое из этого всего - хуже специализированного решения. Но если они удовлетворяют условиям задачи, то они дешевше.

Полнотекст в постгресе никогда не претендовал на построение только поиска, не его это задача. Если вам нужен только поиск - используйте что-нибудь другое. Но если вы используете постгрес для чего-то еще и вам нужен полнотекст - посгтрес предоставляет его.

teodor
()
Ответ на: комментарий от teodor

> Тут посмотри. Похоже, в удалённых внизу.

ага, спасибо за хинт.

2 teodor:

согласен.

siberean
()
Ответ на: комментарий от teodor

но надо также добавить, что юзер привык к гугловскому сёрчу. И если он не найдёт что-то - что он считает - должно быть возвращено - он будет вопить.
Поэтому требования к качеству сёрча очень высокие.
Особенно после концепции "одной коммандной строки для всех задач" гугла.
Люцина старается следовать этим новым стандартам и я боюсь - что посгресс может не угнаться - имплементировать те же фишки так же эффективно.

siberean
()
Ответ на: комментарий от siberean

я имею в виду не http://goosh.org/
а
http://www.geocities.com/ian_springer/google_syntax.html
и то что юзера уже хорошо знают синтаксис и пользуются ими, т.е. он - де-факто стандарт.
Чего и от других сайтов, претендующих на сёрч - требовать будут.

siberean
()
Ответ на: комментарий от siberean

> посгресс может не угнаться - имплементировать те же фишки так же эффективно.

Кто закажет - сделаю :). Парсер запроса, выделяющий имя сайта или географический адрес, должен работать перед полнотекстовым парсером.

teodor
()
Ответ на: комментарий от teodor

Ещё вот что вспомнил по поводу "если вы используете постгрес для чего-то еще и вам нужен полнотекст...".
На http://www.fosslc.org/drupal/node/473
есть лекция по люцине (слушать очень трудно да и лор-эффект может затормозить наш местный, деревенский фосс), но там чувак говорит - что если вы видите - что какой-нибудь CMS использует сёрч - скорее всего - там люцин.
Я пользовался парой - и там действительно был люцин. Не смотря на то - что была и реляционка тоже.
Т.е. разрабы, по-хорошему, не должны быть зависимы от одной конкретной базы (а что если юзер использует оракле, mysql итд?) - поэтому и берут базо-независимое решение - люцину.

siberean
()
Ответ на: комментарий от teodor

будем иметь в виду:)
я всё промываю мозги менеджменту использовать поосгресс для ГИСа, может когда-то и созреют.

siberean
()
Ответ на: комментарий от siberean

> Чувак говорит - что если вы видите - что какой-нибудь CMS использует сёрч - скорее всего - там люцин.

Тяжело так рассуждать. Ко мне почему-то :) не обращаются с вопросами о Люцене, а обращаются с вопросами по постгресу и его поиску.

teodor
()
Ответ на: комментарий от teodor

Только что прошло в голову:
а ведь индексировать как правило - ведь нужно результат, а не поля.
Возьмём ЛОР. Что юзер хочет увидеть? Он хочет увидеть весь тред. Если будем индексировать по полям - не получим булевский сёрч по многим постам (где и "физики" и "слакварь" и "Луговский"). Так как эти 3 токена - просто в разных рекордах. Нужно индексировать результат рендеренья ЖСП.
Для динамических страниц - можно прикрутить (на cronjob) хттп клиент - который будет дёргать страницу и результат слать на люцину (инкрементальный апдейт). И вся страница будет - как целое (как и должно быть - то что видит юзер).
Типа того.
(Не знаю как сделать это с отдельными рекордами)

siberean
()
Ответ на: комментарий от teodor

>Тяжело так рассуждать. Ко мне почему-то :) не обращаются с вопросами о Люцене, а обращаются с вопросами по постгресу и его поиску.

наверное, потому что Вы спец по постгрессу :)?

siberean
()
Ответ на: комментарий от siberean

да, я уже не просто склоняюсь к мысли (в процессе нашего разговора), но и уверен - что надо индексировать только результат, итоговую страницу (картинку, что видит юзер и на что он будет делать запросы). Рекорды - имплементация, юзер не знает как инфа структурирована и не хочет знать.
Т.е. сёрч - чисто внешняя штука.

siberean
()
Ответ на: комментарий от siberean

> Что юзер хочет увидеть?

А бог его знает :) Зависит от системы.

Если взять меня как пользователя, то мне хочется часто:

- найти ответ на вопрос типа "Как пропатчить KDE под FreeBSD?", но не читать флеймы на эту тему

- найти статью про "Как построить обратный индекс" или хотя бы сообщение со ссылками.

Ни одна система сегодня на это не способна, я вынужден приспосабливаться под нее

teodor
()
Ответ на: комментарий от siberean

> да, я уже не просто склоняюсь к мысли (в процессе нашего разговора), но и уверен - что надо индексировать только результат, итоговую страницу (картинку, что видит юзер и на что он будет делать запросы). Рекорды - имплементация, юзер не знает как инфа структурирована и не хочет знать. Т.е. сёрч - чисто внешняя штука.

Как ты думаешь, что найдет такая система при поиске по ЛОРу по запросам "Добавить комментарий" или "Документация" или "Заглавие"? Правильный ответ - почти весь ЛОР. Т.е. несмысловой контент индексироваться не должен. Как это сделать? Два пути:

- Настраивать анализатор страницы, выкидывающий оформление. По этому пути вынуждены идти все внешние поисковики. Внутренние поисковики так не делают из-за очевидно обезьяньей работы - сначала навешаем оформление, а потом будем мучитель определять где что. В качестве бонуса - разборки с аяксом.

- индексировать сам контент, хранящийся где-либо унутре. Паллиативное решение - иметь спецстраницы без оформления чисто для внутреннего индексатора.

teodor
()
Ответ на: комментарий от siberean

> наверное, потому что Вы спец по постгрессу :)?

И соответственно, вывод: все используют постгрес, просто не все обращаются :)

teodor
()
Ответ на: комментарий от teodor

я чётко разделяю 2 сёрча.
- то, где я запрашиваю гугел - на предмет который я никогда не видел и хочу узнать
- где я ищю то что когда-то мне уже попадалось на глаза (и я имею хинты, обрывки из памяти - какие ключевые слова там присутствовали.

В первом случае - я эксплорю.
Во втором - восстанавливаю линк на когда-либо виденное ранее.

Так как весь интернет "построить" никогда не удастся (я имею в виду - построить строгую таксономию, категоризовать всё) - то булевский сёрч (над всем документом как единой единицей) и эвристика - видимо будут применятся всегда.
Видимо, гугловский подход работает хорошо.
это и PageRank, и веса, обратно пропорциональные от расстояния между словами в документе (как целого!), и "наказание" документов, на которые слишком много линков (т.е. редкая инфа приветствуется увеличением веса) и стемизация, нормализация итд итп.
Поэтому все и пользуются гуглом (жаль что яху схавали вчера - я очень горюю по этому поводу - тоже неплохой движок был).
В случае отдельных порталов - линков между документами почти нет, т.е. веса надо раздавать самим - по каким-то конкретным приоритетам.

siberean
()
Ответ на: комментарий от teodor

> Паллиативное решение - иметь спецстраницы без оформления чисто для внутреннего индексатора.

хорошая идея кстати:
отдельная ЖСП, возвращающая чистый поток сознания лора (без титулов).

Но гугел не знает - что оформление, что нет и, видимо, имеет либо эвристику (добавлять регулярно-повторяющиеся вещи - в стоп-слова), либо - "наказывает" - за частоту (вес обратно пропорционален частоте), выделяя редкие слова.

siberean
()
Ответ на: комментарий от siberean

> Что юзер хочет увидеть? Он хочет увидеть весь тред. Если будем индексировать по полям - не получим булевский сёрч по многим постам (где и "физики" и "слакварь" и "Луговский"). Так как эти 3 токена - просто в разных рекордах. Нужно индексировать результат рендеренья ЖСП.

Зачем? Можно сгенерировать один ts_vector по всему треду, для этого нужно только триггер правильный написать. Но тогда не получится делать поиск с фильтрацией автора комментария. Сейчас комментарии ищутся независимо. А вообще как вариант можно попробовать в индексе держать и отдельные комменты, и топики целиком с комментариями. Будет время - поэкспериментирую (но только после перехода на 8.4, сейчас и так не быстро ищет)

maxcom ★★★★★
()
Ответ на: комментарий от maxcom

да, структурированный подход (когда детерминистически надо какое-то поле отсечь или включить) - противоречит общему неструктурированному подходу (когда вся страница рассматривается как сплошой текст, целое и одна формула вычисляет всё), используемому гуглом, люциной и всеми внешними поисковиками. Везде свои недостатки.

siberean
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.