Любой способ выбрать, не вызывая блокировки в MySQL?
Запрос:
SELECT COUNT(online.account_id) cnt from online;
Но онлайн-таблица также модифицируется событием, поэтому часто я вижу блокировку, запустив show processlist
.
Есть ли какая-либо грамматика в MySQL, которая может сделать инструкцию select, не вызывающую блокировки?
И я забыл упомянуть выше, что это в базе данных подчиненных MySQL.
После того, как я добавил в my.cnf:transaction-isolation = READ-UNCOMMITTED
ведомое устройство встретится с ошибкой:
Ошибка "Двоичный журнал невозможен. Сообщение: Уровень транзакции "READ-UNCOMMITTED" в InnoDB небезопасен для режима binlog "ЗАЯВЛЕНИЕ" по запросу
Итак, есть ли совместимый способ сделать это?
Ответы
Ответ 1
Найдена статья под названием "MYSQL WITH NOLOCK"
https://web.archive.org/web/20100814144042/http://sqldba.org/articles/22-mysql-with-nolock.aspx
в MS SQL Server вы должны сделать следующее:
SELECT * FROM TABLE_NAME WITH (nolock)
и эквивалент MYSQL
SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
SET SESSION TRANSACTION ISOLATION LEVEL REPEATABLE READ ;
РЕДАКТИРОВАТЬ
Майкл Миор предложил следующее (из комментариев)
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED ;
SELECT * FROM TABLE_NAME ;
COMMIT ;
Ответ 2
Если таблица InnoDB, см. http://dev.mysql.com/doc/refman/5.1/en/innodb-consistent-read.html - она использует режим согласованного чтения (без блокировки) для SELECT ", которые делают не указывать FOR UPDATE или LOCK IN SHARE MODE, если параметр innodb_locks_unsafe_for_binlog установлен, а уровень изоляции транзакции не установлен в SERIALIZABLE. Таким образом, блокировки не устанавливаются в строках, считанных из выбранной таблицы".
Ответ 3
использование
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED.
Документы версии 5.0 находятся здесь.
Документы версии 5.1 находятся здесь.
Ответ 4
Вы можете прочитать эту страницу руководства по MySQL. Как заблокирована таблица, зависит от типа таблицы.
MyISAM использует блокировки таблиц для достижения очень высокой скорости чтения, но если у вас есть инструкция UPDATE, то будущие SELECTS будут стоять в очереди за UPDATE.
В таблицах InnoDB используется блокировка на уровне строк, и у вас не будет блокировки всей таблицы за UPDATE. Существуют и другие проблемы с блокировкой, связанные с InnoDB, но вы можете найти, что это соответствует вашим потребностям.
Ответ 5
В зависимости от типа таблицы блокировка будет выполняться по-разному, но так будет и счетчик SELECT. Для таблиц MyISAM простая таблица SELECT count (*) FROM не должна блокировать таблицу, так как она обращается к метаданным, чтобы вытащить счетчик записей. Innodb займет больше времени, так как он должен захватить таблицу в снимке для подсчета записей, но он не должен вызывать блокировку.
У вас должно быть как минимум установлено значение concurrent_insert равным 1 (по умолчанию). Затем, если в файле данных нет "пробелов" для заполнения таблицы, в файл будут добавлены вставки, а SELECT и INSERT могут выполняться одновременно с таблицами MyISAM. Обратите внимание, что удаление записи помещает "пробел" в файл данных, который будет пытаться заполняться будущими вставками и обновлениями.
Если вы редко удаляете записи, вы можете установить concurrent_insert равным 2, а вставки всегда будут добавлены в конец файла данных. Затем выбор и вставки могут происходить одновременно, но ваш файл данных никогда не будет уменьшаться, независимо от того, сколько записей вы удаляете (кроме всех записей).
В нижней строке, если у вас много обновлений, вставляет и выбирает на столе, вы должны сделать это InnoDB. Однако вы можете свободно смешивать типы таблиц в системе.
Ответ 6
SELECT обычно не блокируют, что вам нужно, на таблицах InnoDB. Уровень изоляции транзакции по умолчанию означает, что выбор не блокирует материал.
Конечно, все еще происходит.
Ответ 7
От эта ссылка:
Если вы явно блокируете блокировку таблицы с LOCK TABLES, вы можете запросить ПРОЧИТАТЬ ЛОКАЛЬНЫЙ замок, а не ЧИТАТЬ блокировки для включения других сеансов выполнять параллельные вставки, пока вы заблокируйте таблицу.
Ответ 8
другой способ включить грязное чтение в mysql - добавить подсказку: LOCK IN SHARE MODE
SELECT * FROM TABLE_NAME LOCK IN SHARE MODE;