Чем можно заменить like sql
Есть ли альтернатива запросу LIKE в T-SQL?
У меня есть сценарий, где мне нужно выполнить следующую операцию:
Я должен использовать два% (подстановочные знаки) в начале и в конце Url ( ‘% %’ ), поскольку пользователь должен иметь возможность искать полный URL-адрес, даже если он набирает частичный текст. Например, если URL-адрес http://www.google.co.in и типы пользователей «goo», то URL-адрес должен появиться в результатах поиска. Оператор LIKE вызывает проблемы с производительностью. Мне нужна альтернатива, чтобы я мог избавиться от этого утверждения и подстановочных знаков. Другими словами, я не хочу использовать инструкцию LIKE в этом сценарии. Я пытался использовать T-SQL CONTAINS но это не решение моей проблемы. Есть ли другая альтернатива, доступная, чем может выполнять сопоставление образцов и быстро давать результаты?
Запуск вроде% с вызовом сканирования. Не обойти это. Он должен оценивать каждое значение.
Если вы индексируете столбец, это должно быть сканирование индекса (а не таблицы).
У вас нет альтернативы, которая не вызовет сканирование.
Charindex и patindex являются альтернативами, но все равно будут проверять и не устранять проблему с производительностью.
Не могли бы вы разбить компоненты на отдельную таблицу?
WWW
Google
Колорадо
в
А затем выполните поиск на «goo%»?
Это будет использовать индекс, поскольку он не начинается с%.
Еще лучше вы можете искать «google» и искать индекс.
И вы хотели бы, чтобы строка была уникальной в этой таблице с отдельным соединением на Int PK, чтобы она не возвращала несколько www, например.
Подозреваемый FullText Содержит не быстрее, потому что FullText сохранил URL как одно слово.
Насколько мне известно, там нет альтернативы like или contains (полнотекстовый поиск функция), который дал бы более высокую производительность. Что вы можете сделать, это попытаться повысить производительность, оптимизируя ваш запрос. Для этого вам нужно немного узнать о своих пользователях и как они будут использовать вашу систему. Я подозреваю, что большинство людей будут вводить URL-адрес с самого начала адреса (т.е. Без протокола), поэтому вы можете сделать что-то вроде этого:
Это дает вам некоторую оптимизацию; т.е. если URL http://www.google.com, индекс в столбце url можно использовать, так как http://www.goo находится в начале строки. option (fast 1) штука на конце, чтобы убедиться, что это преимущество видно; поскольку последний URL like %searchTerm% не может использовать индексы, мы скорее вернем ответы, как только можем, а не дождаться завершения этой медленной части. Подумайте о других распространенных шаблонах использования и способах их устранения.
Ваш запрос очень простой, и я не вижу причин для его замедления. Dbms wil читает запись для записи и сравнения строк. Обычно это может даже делать это в параллельных потоках.
Как вы думаете, что может быть причиной того, что ваше выражение так медленно? Есть ли в вашей таблице миллиарды записей? Имеются ли в ваших записях столько данных?
Лучше всего не заботиться о запросе, а о базе данных и вашей системе. Другие уже предложили индекс в столбце URL, поэтому вместо сканирования таблицы индекс можно отсканировать. Является ли максимальная степень параллелизма ошибочно установлена? Разбита ли ваша таблица? Соответствует ли ваше оборудование? Это то, что нужно рассмотреть здесь.
Is there and alternative to LIKE statement in T-SQL?
I have a scenario where I need to perform following operation:
I have to use two % (wildcard characters) at the beginning and the end of Url ( ‘% %’ ) as user should be able to search the complete url even if he types partial text. For example, if url is http://www.google.co.in and user types «goo», then the url must appear in search results. LIKE operator is causing performance issues. I need an alternative so that I can get rid of this statement and wildcards. In other words, I don’t want to use LIKE statement in this scenario. I tried using T-SQL CONTAINS but it is not solving my problem. Is there any other alternative available than can perform pattern matching and provide me results quickly?
5 Answers 5
Starting a like with a % is going to cause a scan. No getting around it. It has to evaluate every value.
If you index the column it should be an index (rather than table) scan.
You don’t have an alternative that will not cause a scan.
Charindex and patindex are alternatives but will still scan and not fix the performance issue.
Could you break the components out into a separate table?
www
google
co
in
And then search on like ‘goo%’?
That would use an index as it does not start with %.
Better yet you could search on ‘google’ and get an index seek.
And you would want to have the string unique in that table with a separate join on Int PK so it does not return multiple www for instance.
Suspect FullText Contains was not faster because FullText kept the URL as one word.
You could create a FULLTEXT index.
First create your catalog:
Now you can search the table using CONTAINS:
To my knowledge there’s no alternative to like or contains (full text search feature) which would give better performance. What you can do is try to improve performance by optimising your query. To do that, you need to know a bit about your users & how they’ll use your system. I suspect most people will enter a URL from the start of the address (i.e. without protocol), so you could do something like this:
That then gives you some optimisation; i.e. if the url’s http://www.google.com the index on the url column can be used since http://www.goo is at the start of the string. The option (fast 1) piece on the end’s to ensure this benefit is seen; since the last URL like %searchTerm% can’t make use of indexes, we’d rather return responses as soon as we can rather than wait for that slow part to complete. Have a think of other common usage patterns and ways around those.
As written, your query cannot be further optimized, and there is no way of getting around the LIKE to do your searching. The only thing you can do to improve performance is reduce the SELECT to return only the columns you need if you don’t need all of them, and create an index on URL with those columns included. The LIKE will not be able to use the index for seeking, but the reduced data size for scanning can help. If you have a SQL Server edition that supports compression, that will help as well.
For instance, if you really need only column A, write
And create the index as
If A is already included in your primary key, the INCLUDE is unnecessary.
Your query is a very simple one and I see no reason for it to be slow. The dbms wil read record for record and compare strings. Usually it can even do this in parallel threads.
What do you think can be the reason for your statement being so slow? Are there billions of records in your table? Do your records contain so much data?
Your best bet is not to care about the query, but about the database and your system. Others have already suggested an index on the url column, so rather than scanning the table, the index can be scanned. Is max degree of parallelism mistakenly set? Is your table fragmented? Is your hardware appropriate? These are the things to consider here.
Чем заменить медленный запрос с LIKE?
Есть не очень расторопная БД (FileMaker через ODBC, Mac OS X Server) на 15 тыс. записей с плохой структурой, по которой нужно быстро (менее секунды) делать поиск по одному полю. Поле сборное. В нем хранятся номера телефонов через пробел, например, «5555555 4564472 89184533335».
Поиск делается запросом типа
Работает это очень медленно. Как спасать ситуацию?
Оценить 3 комментария
На всякий случай проверьте, проиндексировано ли поле с телефонами; если нет или index minimal, переставьте на all. Скорее всего, проиндексировано, конечно.
Оптимальный вариант — переделать как советует da0c, только фиксированной длины не надо и пробелами не надо добивать, в FM это бессмысленно. Я тут потестировал одну относительно несложную переделку, но она еще медленнее оказалась.
Если база на сервере и SQL не принципиален, можно через HTTP GET данные запрашивать; данные будут в XML, но при желании в версии до 11 включительно можно их прямо там через XSLT прогнать.
Этого в справке нет, это т. н. XML publishing interface, вот руководство (PDF, к 12-й версии; в 11-й и ранее, думаю, то же самое, но еще и XSLT был на сервере). Кстати, есть и PHP обертка к нему, но я в PHP плохо разбираюсь, поэтому ничего умного не скажу.
Вам нужно убедится, что XML интерфейс присутствует (в контрольной панели сервера это должно быть наглядно видно), разрешить доступ к вашей БД через XML (в настройках учетных записей и привилегий создайте подходящую запись — для тестирования удобно guest — назначьте ей, скажем, встроенный набор привилегий только для чтения ([Read-Only Access]) и в его настройках отметьте Access via XML Web Publishing, после чего попробуйте послать GET-запрос вида:
Должен вернуть список доступных БД в XML. Если работает, то поиск телефонов будет примерно такой:
Там есть еще операторы поиска, но в вашем случае операторы не нужны.
Разница между LIKE и = в MYSQL?
в чем разница между
12 ответов
как можно сделать сопоставление:
Если вам не нужно сопоставление шаблонов, используйте = вместо LIKE. Это быстрее и безопаснее. (Вы используете параметризованные запросы, верно?)
= в SQL делает точное соответствие.
как делает шаблоны, с помощью ‘%’ в качестве многофункционального символ-матч и ‘_’ в качестве одного символа символ матча. «\»является escape-символом по умолчанию.
foobar = ‘$foo’ и foobar LIKE ‘$foo’ будет вести себя одинаково, потому что ни одна строка не содержит подстановочный знак.
foobar LIKE ‘%foo’ будет соответствовать чему-либо, заканчивающемуся на «foo».
пожалуйста, имейте в виду, что MySQL будет делать отливки в зависимости от ситуации: LIKE будет выполнять строковое литье, тогда как = будет выполнять int cast. Учитывая ситуацию:
выбрать * От test как LEFT JOIN test как b на a.field1 как b.field2
выбрать * От test как LEFT JOIN test как b на a.field1 = б.поле2
по данным справочная страница MYSQL, конечные пробелы значимы в LIKE, но не =, и вы можете использовать подстановочные знаки, % для любых символов и _ точно для одного символа.
Я думаю, что с точки зрения скорости = быстрее, чем нравится. Как указано, = делает точное совпадение и, как можно использовать подстановочный знак, если это необходимо.
Я всегда использую = знак, когда я знаю значения чего-то. Например
тогда для подобных я использую такие вещи, как:
Если вы используете Oracle Developers Tool, вы можете протестировать его с помощью Explain, чтобы определить влияние на базу данных.
конечный результат будет таким же, но механизм запросов использует другую логику для получения ответа. Как правило, такие запросы записывают больше циклов, чем запросы»=». Но когда подстановочный знак не указан, я не уверен, как оптимизатор может относиться к этому.
С пример в вашем вопросе нет никакой разницы.
но, как сказал Джесси, вы можете сделать сопоставление подстановочных знаков
Подробнее:
немного OG google не повредит.
предложение WHERE со знаком равенства ( = ) отлично работает, если мы хотим сделать точное совпадение. Но может быть требование, когда мы хотим отфильтровать все результаты, где «foobar «должен содержать»foo». Это можно обработать с помощью предложения SQL LIKE вместе с предложением WHERE.
Если предложение SQL LIKE используется вместе с символами%, оно будет работать как подстановочный знак.
без символа % как предложение очень аналогично знаку равенства вместе с предложением WHERE.
в вашем примере они семантически равны и должны возвращать один и тот же вывод.
однако, как даст вам возможность сопоставления шаблонов с подстановочными знаками.
вы также должны отметить, что = может дать вам повышение производительности в некоторых системах, поэтому, если вы, например, ищете номер exakt, = будет предпочтительным методом.
как вы выразились, нет никакой разницы.
это потенциально может быть медленнее, но я уверен, что MySQL понимает, что в строке поиска нет подстановочных знаков, поэтому он не будет делать, как скороговорка соответствия в конце концов, так что на самом деле, никакой разницы.
в моем случае я найти Like быть быстрее, чем =
Like получил несколько строк в 0.203 секунд в первый раз, а затем 0.140 секунд
= возвращает те же строки в 0.156 секундах постоянно
пример: у меня есть таблица с полем » ID «(тип: int (20) ) и запись, содержащая значение»123456789»
найдена запись с (неверный результат)
запись не найдена (это правильно)
Итак, по крайней мере, для целых полей это кажется важным разница.
Что быстрее-INSTR или LIKE?
Если ваша цель состоит в том, чтобы проверить, существует ли строка в столбце MySQL (типа «varchar», «text», «blob» и т. д.), который из следующих быстрее / эффективнее / лучше использовать, и почему?
или есть какой-то другой метод, который превосходит любой из них?
4 ответов
полнотекстовый поиск абсолютно будет быстрее, как отметил кибибу в комментариях выше.
Если вы не выполняете поиск префикса в индексированном столбце:
в этом случае, как только суффикс подстановочный знак намного быстрее.
для меня INSTR и найти выполняется быстрее всего:
в случае » переднего wilcard «(т. е. «как»%. «предикат), как это, по-видимому, имеет место здесь,INSTR и LIKE должны выполнять примерно то же самое.
когда Джокер не «передний подстановочный знак», подобный подход должен быть быстрее, если подстановочный знак не очень избирательный.
причина почему тип подстановочного знака и его избирательность имеют значение это предикат с INSTR () будет систематически результат сканирования таблицы (SQL не может делать никаких предположений о семантике INSTR), в результате чего SQL может использовать свое понимание семантики подобного предиката, чтобы, возможно, использовать индекс, чтобы помочь ему протестировать только уменьшенный набор возможных совпадений.
Как предложено в комментарии к самому вопросу,полнотекстовый индекс будет намного быстрее. Разница зависит от конкретного распределения слов в тексте, а также общего размера таблицы и т. д. но ожидайте что-нибудь от вдвое быстрее, может быть, в 10 раз быстрее.
возможный недостаток использования в полнотекстовом индексе, в дополнение к общим накладным расходам для создания такого индекса, заключается в том, что, если вы не очень осторожны в настройке этого индекса (например, определение списка стоп-слов, используя конкретный синтаксис поиска, чтобы избежать инфлективных форм и тому подобное. ), могут быть случаи, когда результаты, предоставленные FullText, не будут ожидаемыми. Например, поиск » пилы «(инструмента рубить дрова), можно получить много хитов для записей, включая глагол «видеть», в его различных спрягаемых формах.
Конечно, эти лингвистические функции полнотекстовых индексов обычно можно переопределить, а также можно считать, что такие функции фактически являются преимуществом, а не недостатком. Я просто упоминаю об этом здесь, так как мы сравниваем это с простой поиск по шаблону.
мало что можно добавить к тесту раззеда. Но, по-видимому, используя regexp нести гораздо тяжелее нагрузки, как сет указывает в своем комментарии.
следующие тесты предполагают, что вы установили query_caching до On в моем.ini
тесты
тайминги показывают среднюю производительность, из трех измерений (с очищенным кэшем периодически):
начальный: 0.0035 s
кэширование: 0.0005 s
начальный: 0.01 s
кэширование: 0.0004 s
результат
хотя и минимальная, разница во времени кэша, вероятно, достаточна для дальнейшего расследования.
в Вероятно настроенной системе MySQL полнотекстовое индексирование обычно должно быть всегда быстрее или, по крайней мере, на одном уровне с неиндексированным поиском. Поэтому используйте индексацию, особенно на длинных текстах на человеческом языке, независимо от прерывистого кода разметки.