Я хотел бы использовать регулярное выражение в sqlite, но я не знаю, как это сделать.
В моей таблице есть столбец со строками: "3,12,13,14,19,28,32" Теперь, если я набираю "where x LIKE" 3 ", я также получаю строки, которые содержат значения, такие как 13 или 32, но я хотел бы получить только строки, которые имеют точно значение 3 в этой строке.
Кто-нибудь знает, как это решить?
SQLite3 поддерживает оператор REGEXP:
WHERE x REGEXP <regex>
regex()
для поддержки оператора REGEXP
? По умолчанию пользовательская функция не была добавлена.
Как уже указывали другие, REGEXP вызывает пользовательскую функцию, которая должна быть сначала определена и загружена в базу данных. Может быть, некоторые дистрибутивы sqlite или инструменты GUI включают его по умолчанию, но моя установка Ubuntu этого не сделала. Решение было
sudo apt-get install sqlite3-pcre
который реализует регулярные выражения Perl в загружаемом модуле в /usr/lib/sqlite3/pcre.so
Чтобы использовать его, вы должны загружать его каждый раз, когда открываете базу данных:
.load /usr/lib/sqlite3/pcre.so
Или вы можете поместить эту строку в ваш ~/.sqliterc
.
Теперь вы можете запросить так:
SELECT fld FROM tbl WHERE fld REGEXP '\b3\b';
Если вы хотите сделать запрос непосредственно из командной строки, вы можете использовать переключатель -cmd
для загрузки библиотеки перед вашим SQL:
sqlite3 "$filename" -cmd ".load /usr/lib/sqlite3/pcre.so" "SELECT fld FROM tbl WHERE fld REGEXP '\b3\b';"
Если вы работаете в Windows, я думаю, что аналогичный файл .dll должен быть где-то доступен.
Хакерный способ решить его без регулярного выражения where ',' || x || ',' like '%,3,%'
x
перед тестированием - это должно работать ..
SQLite по умолчанию не содержит функций регулярного выражения.
Он определяет оператор REGEXP
, но это приведет к ошибке с сообщением об ошибке, если вы или ваша инфраструктура не определите функцию пользователя под названием regexp()
. Как вы это сделаете, это будет зависеть от вашей платформы.
Если у вас установлена функция regexp()
, вы можете сопоставить произвольное целое из списка, разделенного запятыми, следующим образом:
... WHERE your_column REGEXP "\b" || your_integer || "\b";
Но на самом деле, похоже, вы найдете вещи намного проще, если вы нормализировали структуру своей базы данных, заменив те группы в пределах одного столбца с отдельной строкой для каждого номера в списке, разделенном запятыми. Тогда вы можете не только использовать оператор =
вместо обычного выражения, но также использовать более мощные средства реляционной обработки, такие как объединения, которые предоставляет вам SQL.
SQLite UDF в PHP/PDO для ключевого слова REGEXP
, который имитирует поведение в MySQL:
$pdo->sqliteCreateFunction('regexp',
function ($pattern, $data, $delimiter = '~', $modifiers = 'isuS')
{
if (isset($pattern, $data) === true)
{
return (preg_match(sprintf('%1$s%2$s%1$s%3$s', $delimiter, $pattern, $modifiers), $data) > 0);
}
return null;
}
);
Модификатор u
не реализован в MySQL, но я считаю полезным использовать его по умолчанию. Примеры:
SELECT * FROM "table" WHERE "name" REGEXP 'sql(ite)*';
SELECT * FROM "table" WHERE regexp('sql(ite)*', "name", '#', 's');
Если значение $data
или $pattern
равно NULL, результат будет NULL - так же, как в MySQL.
UPDATE TableName
SET YourField = ''
WHERE YourField REGEXP 'YOUR REGEX'
И:
SELECT * from TableName
WHERE YourField REGEXP 'YOUR REGEX'
Нехорошо ответить на вопрос, который был опубликован почти год назад. Но я пишу это для тех, кто считает, что Sqlite сам предоставляет функцию REGEXP.
Одно базовое требование для вызова функции REGEXP в sqlite - это
"Вы должны создать свою собственную функцию в приложении, а затем предоставить ссылку обратного вызова для драйвера sqlite.
Для этого вам нужно использовать sqlite_create_function (интерфейс C). Вы можете найти деталь из здесь и здесь
мое решение в python с sqlite3:
import sqlite3
import re
def match(expr, item):
return re.match(expr, item) is not None
conn = sqlite3.connect(':memory:')
conn.create_function("MATCHES", 2, match)
cursor = conn.cursor()
cursor.execute("SELECT MATCHES('^b', 'busy');")
print cursor.fetchone()[0]
cursor.close()
conn.close()
если регулярное выражение совпадает, выход будет равен 1, иначе 0.
Подумайте об использовании этого
WHERE x REGEXP '(^|,)(3)(,|$)'
Это будет соответствовать точно 3, когда x находится:
Другие примеры:
WHERE x REGEXP '(^|,)(3|13)(,|$)'
Это будет соответствовать 3 или 13
Вы можете использовать регулярное выражение с REGEXP, но это глупый способ сделать точное совпадение.
Вы должны просто сказать WHERE x = '3'
.
Исключительное предложение or'ed where, которое может сделать это без конкатенации строк:
WHERE ( x == '3' OR
x LIKE '%,3' OR
x LIKE '3,%' OR
x LIKE '%,3,%');
Включает точное соответствие по четырем случаям, конец списка, начало списка и средний список.
Это более подробный, не требует расширения регулярного выражения.
Если вы используете php, вы можете добавить любую функцию в ваш оператор sql, используя: SQLite3:: createFunction. В PDO вы можете использовать PDO:: sqliteCreateFunction и реализовать preg_match в вашем заявлении:
Посмотрите, как это сделано Havalite (RegExp в SqLite с использованием Php)