Вопрос

Я предлагаю возможность поиска для своих пользователей.Они могут искать по названию города.Проблема в том, что названия моих городов, которые я сохранил, такие как «Сент-Луис».Но я хочу найти Сент-Луис, даже если пользователь введет «Сент-Луис».Луи» или «Сент-Луис».Есть какие-нибудь предложения о том, как я мог бы создать таблицу поиска, чтобы как-то это учесть?

Это было полезно?

Решение

Создавать два столы.

В одном собрано все о городе.

Один содержит кучу названий городов, а внешний ключ связывает эти названия с идентификатором первой таблицы.Итак, у вас есть связь «один ко многим» между city и city_names.

Теперь единственной проблемой является различение одного названия для каждого города, которое является предпочтительным.Мы можем сделать это несколькими способами:1) первая таблица может иметь fk для второй таблицы, которая соответствует идентификатору предпочтительного имени.Однако это создает циклическую зависимость.Так что лучше: 2) просто добавьте логический/битовый столбец во вторую таблицу is_preffered.

create table city (id not null primary key, other columns ) ;

create table city_name (
 id not null primary key, 
 city_id int references city(id), 
 name varchar(80),
 is_preferred bool  
) ;

Затем, чтобы получить все имена, сначала с предпочтительным именем:

   select name from city_names where city_id = ? 
   order by is_preffered desc, name;

Это имеет дополнительное преимущество:если вы не охватываете все города и поселки, вы можете использовать вторую таблицу, чтобы сопоставить города/деревни/округа, которые вы не охватываете, с крупными городами, которые вы охватываете:

 insert into city_name(city_id, name) values
 ( $id-for-New-York-City, 'New York'),
 ( $id-for-New-York-City, 'Manhattan'),
 ( $id-for-New-York-City, 'Big Apple'),
 ( $id-for-New-York-City, 'Brooklyn');

Другие советы

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

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

Итак, в вашем случае в shorthand-to-normal стол у нас будет

 ______________
| short|normal |
|______|_______|
|St    |Saint  |
|St.   |Saint  |

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

Я вижу несколько возможных способов справиться с этим.Один из них Саундекс алгоритм поиска, который соответствует сходству английских строк.Более того, это поддерживается изначально в некоторых базах данных, таких как PostgreSQL.

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

В качестве общего подхода вы можете нормализовать элементы как при вставке, так и при поиске в них.

Правила нормализации могут быть:

Saint => St
St. => St

и т. д.

Тогда нормализованные имена должны совпадать.

ИМХО, я бы оставил базу данных в покое и вместо этого имел бы в вашем приложении список городов.Проще, чище и не требует особых затрат.

Мне нравится вариант в первом ответе.

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

то есть

Нью-Йорк – официальное название.

Теги этого города можно перечислить (Манхэттен, Нью-Йорк, Нью-Йорк, город, большое яблоко..) и т. д.но вам не нужен весь этот мусор в вашей основной таблице Cities или создание связанных дочерних таблиц и необходимость выполнения соединений.Так что просто разместите его в столбцах и выполните поиск по поисковому запросу, а затем верните правильное имя, если оно найдено.

Вы можете использовать встроенные свойства SQL FTS для записей тезауруса.Это позволяет вам создавать собственную карту слов внутри полнотекстового поиска.Таким образом, вы сможете хранить все внутри FTS, а не смешивать FTS и другие запросы.

Не уверен, какую версию SQL вы используете, поскольку она отличается от версии 2005/8, поэтому здесь есть хорошее пошаговое руководство для 2005/8. http://arcanecode.com/2008/05/28/creating-custom-thesaurus-entries-in-sql-server-2005-and-2008-full-text-search/

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top