Поиск телефонных номеров в MySQL - PullRequest
11 голосов
/ 03 сентября 2008

У меня есть таблица, заполненная произвольно отформатированными телефонными номерами, например,

027 123 5644
021 393-5593
(07) 123 456
042123456

Мне нужно найти номер телефона в аналогично произвольном формате (например, 07123456 должен найти запись (07) 123 456

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

digits_only = lambda{ |n| n.gsub /[^\d]/, '' }

needle = digits_only[input_phone_number]
haystack.map(&digits_only).include?(needle)

Суть в том, что мне нужно сделать это в MySQL. У него есть множество строковых функций, ни одна из которых, кажется, не выполняет то, что я хочу.

В настоящее время я могу думать о 2 «решениях»

  • Взломайте франк-запрос CONCAT и SUBSTR
  • Вставьте % между каждым символом иглы (вот так: %0%7%1%2%3%4%5%6%)

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

Обновление: работает с относительно фиксированным набором данных, возможно, с несколькими сотнями строк. Я просто не хотел делать что-то смехотворно плохое, чтобы будущие программисты заплакали.

Если набор данных будет расти, я использую метод phoneStripped. Спасибо за все отзывы!


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

Меня не беспокоит, что результат будет числовым. Главные персонажи, которых я должен рассмотреть: +, -, (, ) и space Так будет ли это решение выглядеть так?

SELECT * FROM people 
WHERE 
REPLACE(REPLACE(REPLACE(REPLACE(REPLACE(phonenumber, '('),')'),'-'),' '),'+')
LIKE '123456'

Разве это не было бы ужасно медленно?

Ответы [ 15 ]

0 голосов
/ 26 мая 2009

возможное решение можно найти по адресу http: //udf-regexp.php-baustelle.de/trac/

.

необходимо установить дополнительный пакет, затем вы можете играть с REGEXP_REPLACE

0 голосов
/ 03 сентября 2008

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

0 голосов
/ 03 сентября 2008

Горе это я. Я закончил тем, что сделал это:

mre = mobile_number && ('%' + mobile_number.gsub(/\D/, '').scan(/./m).join('%'))

find(:first, :conditions => ['trim(mobile_phone) like ?', mre])
0 голосов
/ 03 сентября 2008

Просто идея, но не могли бы вы использовать Regex, чтобы быстро удалить символы, а затем сравнить с тем, что предлагал @Matt Hamilton?

Может быть, даже настроить представление (не уверенное в mysql в представлениях), которое будет содержать все номера телефонов, вырезанные регулярным выражением, в обычный номер телефона?

0 голосов
/ 03 сентября 2008

MySQL может выполнять поиск по регулярным выражениям.

Конечно, но с учетом произвольного форматирования, если бы мой стог сена содержал "(027) 123 456" (имейте в виду, что положение пробелов может измениться, это может быть просто 027 12 3456, и я хотел бы сопоставить его с 027123456, если бы поэтому регулярное выражение должно быть этим?

"^[\D]+0[\D]+2[\D]+7[\D]+1[\D]+2[\D]+3[\D]+4[\D]+5[\D]+6$"

(на самом деле было бы хуже, поскольку руководство mysql, похоже, не указывает, что оно поддерживает \D)

Если это так, разве это не более или менее совпадает с моей идеей %%%%%?

...