Почему разработчики должны разбираться в блокировках базы данных?

Java задняя часть база данных MySQL

1. Блокировать?

1.1 Что такое замок

Значение замка на самом деле таково: закрытый объект, открываемый ключом или паролем. Блокировки в компьютерах обычно используются для управления одновременным доступом к общим ресурсам.Например, блокировка и синхронизация, которые знакомы нашим студентам Java, являются нашими общими блокировками. Конечно, в нашей базе данных есть блокировки для контроля одновременного доступа к ресурсам, что является одним из отличий между базой данных и файловой системой.

1.2 Зачем нужно разбираться в блокировках базы данных?

Вообще говоря, рядовым разработчикам достаточно понимать DQL (выбрать), DML (вставить, обновить, удалить) при использовании базы данных.

Сяо Мин — инженер Java-разработчик, только что закончивший учебу и работающий в интернет-компании.Его обычная работа — выполнять требования PM.Конечно, он не может выйти за рамки spring, springmvc и mybatis при выполнении требований, поэтому вообще говоря, SQL по-прежнему его собственный.Рукописные, столкнуться с более сложным SQL пойдет на Baidu из Интернета. Для некоторых более важных операций, таких как транзакции, Xiaomi будет использовать Spring транзакции для управления транзакциями базы данных.Из-за относительно небольшого объема данных распределенные транзакции в настоящее время не задействованы.

Несколько месяцев назад Сяомин хорошо провел время. Я знал, что однажды Сяомин получил запрос. У продавца есть элемент конфигурации, называемый элементом конфигурации скидки. Вы можете настроить такие правила, как: купи один, получи один бесплатно, купи один, получи два бесплатно и т. д. Конечно, эти конфигурации передаются на бэкэнд пакетами, поэтому есть проблема, что каждое правило должно соответствовать, удаляет ли он, добавляет или изменяет, поэтому логика бэкэнда более хлопотна, Умный Сяомин подумал способа удалить конфигурацию этого продавца напрямую. , а затем добавить их все. Сяо Мин немедленно завершил разработку и успешно вышел в сеть.

Нет ничего плохого в выходе в онлайн, но в журнале часто появляются некоторые исключения mysql-insert-deadlock. Поскольку опыт Сяо Мина относительно нечастый, я впервые встречаю такой вопрос, поэтому я спросил старого водителя их группы - Дахуна, когда Дахун увидел этот вопрос, и, прочитав его код, он вывел несколько команд и прочитал несколько журналов A, сразу же обнаружил проблему и сказал Сяо Мину: Это связано с тем, что при удалении будет добавлена ​​блокировка пробела, но блокировки пробела совместимы, но при вставке новых данных он будет заблокирован блокировкой пробела из-за к блокировке намерения вставки. , в результате чего обе стороны будут заняты ресурсами друг друга, что приведет к взаимоблокировке. Выслушав это, Сяо Мин, казалось, понял, но из-за того, что о Дахун было так много всего, было неудобно постоянно беспокоить Дахуна, поэтому он решил спуститься и подумать сам. После работы Сяомин вспомнил, что сказал Дахун, что такое гэп-блокировка и что такое блокировка намерения вставки.Похоже, что как разработчик вы должны не только писать SQL для базы данных, иначе вы не сможете решить некоторые трудноизлечимые заболевания. Подумав об этом, Сяо Мин встал на путь невозврата, чтобы изучить блокировку Mysql.

2.InnoDB

2.1архитектура mysql

Сяо Мин не спешил раскрывать эти знания, он впервые узнал об архитектуре Mysql:

Можно обнаружить, что Mysql состоит из компонентов пула соединений, служб управления и компонентов инструментов, компонентов интерфейса sql, компонентов анализатора запросов, компонентов оптимизатора, компонентов буфера, подключаемых механизмов хранения и физических файлов.

Сяо Мин обнаружил, что механизм хранения в mysql предоставляется в виде подключаемого модуля.В MySQL есть много механизмов хранения, и каждый из них имеет свои особенности. Затем Сяо Мин набрал в командной строке:

show engines \G;

На первый взгляд существует так много видов двигателей.

Затем введите следующую команду, чтобы просмотреть механизм по умолчанию для текущей базы данных:

show variables like '%storage_engine%';

Сяо Мин вдруг понял: "Оказалось, что его база данных была InnoDB, и он смутно помнил, что слышал о движке под названием MyIsAM, когда учился в школе. Сяо Мин подумал, в чем разница между ними? Немедленно поискал информацию:

Контраст InnoDB MyIsAM
дела служба поддержки не поддерживается
Замок Поддержка блокировки строки MVCC блокировка стола
иностранный ключ служба поддержки не поддерживается
место хранения Место для хранения большое из-за необходимости кэша сжимаемый
Применимая сцена Есть определенное количество обновлений и вставок много вариантов

Сяомин имеет общее представление о разнице между InnoDB и MyIsAM.Поскольку используется InnoDB, у Сяомина нет слишком большой запутанности.

2.2 Изоляция транзакций

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

2.2.1 Грязные чтения

Одна транзакция считывает незафиксированные обновления в другую транзакцию. Что это обозначает?

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where id = 1; begin;
3 update user set namm = 'test' where id = 1;
4 select * from user where id = 1;
5 commit; commit;

В транзакциях A и B транзакция A запрашивает данные с id=1 в пользовательской таблице в моменты времени 2 и 4 соответственно, но транзакция B изменяется в момент времени 3, что приводит к запросу транзакции A в момент 4. Результат фактически модифицируется транзакцией B. Нарушена изоляция в базе данных.

2.2.2 Неповторяющееся чтение

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

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where id = 1; begin;
3 update user set namm = 'test' where id = 1;
4 commit;
5 select * from user where id = 1;
6 commit;

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

2.2.3 Фантомное чтение

Транзакция считывает зафиксированные данные вставки другой транзакции.

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where id > 1; begin;
3 insert user select 2;
4 commit;
5 select * from user where id > 1;
6 commit;

В транзакции A идентификатор больше 1 запрашивается дважды, и в первом результате запроса нет данных с идентификатором больше 1, но поскольку транзакция B вставила фрагмент данных с id=2, транзакция A может найти его в второй запрос Данные вставлены в транзакцию B.

Изоляция в транзакциях:

уровень изоляции грязное чтение неповторяемое чтение галлюцинации
Чтение незафиксированных (RUC) NO NO NO
Чтение подтверждено (RC) YES NO NO
Повторяемое чтение (RR) YES YES NO
Сериализуемый YES YES YES

Сяомин заметил, что в процессе сбора данных некоторые данные были записаны в InnoDB, которая немного отличается от других баз данных.Повторяемое чтение InnoDB действительно может решить проблему фантомного чтения.Сяомин подумал: "Эта InnoDB довольно крутая, я должен хорошенько присмотреться". посмотрите, как это работает.

2.3 Типы блокировки InnoDB

Сяо Мин сначала поймет, какие общие типы блокировок существуют в Mysql:

2.3.1 S or X

В InnoDb реализованы две стандартные блокировки на уровне строк, которые можно просто рассматривать как две блокировки чтения-записи:

  • S-общая блокировка: также известная как блокировка чтения, другие транзакции могут продолжать добавлять общие блокировки, но не могут продолжать добавлять эксклюзивные блокировки.
  • Х-эксклюзивная блокировка: также называется блокировкой записи, после добавления блокировки записи другие транзакции не могут быть заблокированы.

Совместимость: это означает, что после того, как транзакция A получает определенный тип блокировки для определенной строки, транзакция B также пытается получить определенный тип блокировки для этой строки.Если ее можно получить немедленно, говорят, что блокировка совместима, в противном случае это называется конфликт.

Вертикальная ось представляет существующие блокировки, а горизонтальная ось представляет блокировки, которые пытались получить.

. X S
X конфликт конфликт
S конфликт совместимый

2.3.2 Блокировка намерения

Блокировки намерения — это блокировки уровня таблицы в InnoDB, и, как и их название, они используются для выражения того, что транзакция хочет получить. Намеренные блокировки делятся на:

  • Intent Shared Lock: указывает, что транзакция хочет получить общую блокировку определенных строк в таблице.
  • Преднамеренная монопольная блокировка: указывает, что транзакция хочет получить монопольную блокировку определенных строк в таблице.

Для чего этот замок? Зачем тебе этот замок? Прежде всего, если такой блокировки нет, если вы хотите добавить блокировку таблицы в эту таблицу, общая практика состоит в том, чтобы пройтись по каждой строке, чтобы увидеть, есть ли у него блокировка строки, что слишком неэффективно, и если мы намеренно блокировки, нам нужно только судить, можете ли Вы заблокировать намеренно, вам не нужно сканировать строку за строкой.

Поскольку InnoDB поддерживает блокировки на уровне строк, совместимость блокировок InnboDB можно расширить следующим образом:

. IX IS X S
IX совместимый совместимый конфликт конфликт
IS совместимый совместимый конфликт совместимый
X конфликт конфликт конфликт конфликт
S конфликт совместимый конфликт совместимый

2.3.3 Самоувеличивающаяся блокировка

Саморасширяющаяся блокировка — это специальный механизм блокировки таблицы, повышающий производительность параллельной вставки. У этого замка есть несколько особенностей:

  • Блокировка снимается после выполнения sql, а не выполнения транзакции.
  • Для Вставки... выберите вставки больших данных, которые повлияют на производительность вставки, потому что это заблокирует выполнение другой транзакции.
  • Алгоритм автоинкремента можно настроить.

После версии MySQL 5.1.2 появилось много оптимизаций, и способ самоувеличивающихся блокировок можно настроить в соответствии с различными режимами. Сяомин увидел, что он открыл свой собственный MySQL и обнаружил, что это 5.7, поэтому он ввел следующий оператор, чтобы получить текущий режим блокировки:

mysql> show variables like 'innodb_autoinc_lock_mode';
+--------------------------+-------+
| Variable_name            | Value |
+--------------------------+-------+
| innodb_autoinc_lock_mode | 2     |
+--------------------------+-------+
1 row in set (0.01 sec)

Существует 3 режима конфигурации для innodb_autoinc_lock_mode в MySQL: 0, 1, 2, соответствующие «традиционному режиму», «непрерывному режиму», «режиму с чередованием» соответственно.

  1. Традиционный режим: то есть блокировка таблицы, которую мы чаще всего используем.
  2. Непрерывный режим: мьютекс используется для количества строк, которые можно определить при вставке, а режим блокировки таблицы используется для количества строк, которые не могут быть определены.
  3. Чередующийся режим: Все используют мьютексы. Почему он называется чередующимся режимом? Возможно, что автоинкремент не является непрерывным при вставке в пакетах. обычно выбирается, и производительность является лучшей.

2.4 Алгоритм блокировки InnoDB

Сяо Мин узнал о типах блокировок в InnoDB, но то, как использовать эти блокировки, зависит от алгоритма блокировки.

2.4.1 Блокировка записи

Блокировка записи блокирует запись.Здесь следует отметить, что здесь блокируется индексная запись, а не наша реальная запись данных.

  • Если блокировка является индексом, не являющимся первичным ключом, она заблокирует свой собственный индекс, а затем заблокирует его на первичном ключе.
  • Если в таблице нет индекса (включая первичный ключ), для блокировки будет использоваться скрытый индекс первичного ключа.
  • Если блокируемый столбец не имеет индекса, будет выполнена полная блокировка записи таблицы.

2.4.2 Блокировка зазора

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

2.4.3 блокировка следующего ключа

Эта блокировка по существу представляет собой блокировку записи плюс блокировку пробела. При уровне изоляции RR (InnoDB по умолчанию) Innodb использует этот алгоритм для блокировки сканирования строк, но если в сканировании запроса есть уникальный индекс, он выродится только в блокировку записей. Зачем? Поскольку уникальный индекс может определять количество строк, а другие индексы не могут определять количество строк, возможно, что данные этого индекса будут снова добавлены в другие транзакции, что приведет к фантомным чтениям.

Это также объясняет, почему Mysql может решать фантомные чтения на уровне RR.

2.4.4 Вставка блокировки намерения

Вставьте официальное объяснение блокировки намерения Mysql:

An insert intention lock is a type of gap lock set by INSERT operations prior to row insertion. This lock signals the intent to insert in such a way that multiple transactions inserting into the same index gap need not wait for each other if they are not inserting at the same position within the gap. Suppose that there are index records with values of 4 and 7. Separate transactions that attempt to insert values of 5 and 6, respectively, each lock the gap between 4 and 7 with insert intention locks prior to obtaining the exclusive lock on the inserted row, but do not block each other because the rows are nonconflicting.

Можно видеть, что блокировка намерения вставки генерируется во время вставки.Когда несколько транзакций одновременно записывают разные данные в один и тот же интервал индекса, нет необходимости ждать завершения других транзакций, и ожидание блокировки не будет происходить. Предположим, что есть индекс записи, содержащий значения ключа 4 и 7, и разные транзакции вставляют соответственно 5 и 6. Каждая транзакция будет генерировать блокировку намерения вставки между 4 и 7, чтобы получить монопольную блокировку на вставленную строку, но не будет заблокированы друг с другом, потому что строки данных не конфликтуют.

Здесь следует отметить, что если есть блокировка пробела, блокировка намерения вставки будет заблокирована.

2.5 MVCC

MVCC, технология управления многоверсионным параллелизмом. В InnoDB два скрытых столбца добавляются после каждой строки записей для записи номера версии создания и номера версии удаления. Благодаря номерам версий и блокировкам строк повышается одновременная производительность системы баз данных.

В MVCC есть два типа чтения для операций чтения:

  • Чтение моментального снимка: чтение исторических данных, простой оператор выбора, без блокировки, MVCC реализует повторяемое чтение, используя механизм MVCC для чтения зафиксированных данных при отмене. Таким образом, его чтение не блокируется.
  • Текущее чтение: операторы, которые необходимо заблокировать, обновить, вставить, удалить, выбрать... для обновления и т. д., являются текущими чтениями.

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

Каждый моментальный снимок, прочитанный на уровне изоляции RC, создает новый моментальный снимок.

Конкретный принцип заключается в том, что в каждой строке будет два скрытых поля, одно используется для записи текущей транзакции, а другое используется для записи отката, указывающего на Undolog. Используя undolog, вы можете прочитать предыдущий снимок без создания отдельной записи пространства.

3. Анализ блокировки

К настоящему времени Сяомин получил много базовых знаний о блокировках MySQL, поэтому он решил самостоятельно создать таблицу для проведения экспериментов. Сначала создайте простую пользовательскую таблицу:

CREATE TABLE `user` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `name` varchar(11) CHARACTER SET utf8mb4 DEFAULT NULL,
  `comment` varchar(11) CHARACTER SET utf8 DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `index_name` (`name`)
) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin;

Затем вставьте несколько фрагментов экспериментальных данных:

insert user select 20,333,333;
insert user select 25,555,555;
insert user select 20,999,999;

Изоляция транзакций базы данных выбирает RR

3.1 Эксперимент 1

Сяо Мин открывает две транзакции и проводит первый эксперимент.

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where name = '555' for update; begin;
3 insert user select 31,'556','556';
4 ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

Сяомин открыл две транзакции и ввел приведенный выше оператор и обнаружил, что время ожидания транзакции B действительно истекло. Сяомин посмотрел на блокировку строки с именем = 555. Почему я хотел вставить имя = 556 и заблокировал меня? Итак, Сяо Мин открыл командную строку и ввел:

select * from information_schema.INNODB_LOCKS

Обнаружено, что блокировка следующего ключа добавляется к 555 в транзакции A. Когда транзакция B вставляется, блокировка намерения вставки будет вставлена ​​первой, поэтому можно сделать следующие выводы:

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

3.2 Эксперимент 2

Сяомин обнаружил, что в приведенных выше условиях запроса использовались обычные неуникальные индексы, поэтому Сяомин попробовал индекс первичного ключа:

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where id = 25 for update; begin;
3 insert user select 26,'666','666';
4 Query OK, 1 row affected (0.00 sec)

Records: 1 Duplicates: 0 Warnings: 0

Выясняется, что транзакция B не заблокирована. Эй, что происходит? Сяомин немного запутался. Согласно процедуре эксперимента 1, она должна быть заблокирована, потому что между 25 и 30 блокировками будут промежутки. Поэтому Сяо Мин снова прибегнул к командной строке и обнаружил, что добавлена ​​только блокировка записи X. Получается, что уникальный индекс понизит блокировку записи. Причина этого в том, что неуникальный индекс плюс блокировка следующего ключа могут не определить точное количество строк. Другие транзакции могут добавлять данные этого индексируйте снова во время процесса запроса, что приводит к нарушению изоляции, также известному как фантомное чтение. Поскольку уникальные индексы определяют уникальные строки данных, нет необходимости добавлять блокировки пробелов для устранения фантомных чтений.

3.3 Эксперимент 3

Индекс первичного ключа и неуникальный индекс проверены выше.Также есть поле без индекса.Что будет если его заблокировать?

момент времени Транзакция А Транзакция Б
1 begin;
2 select * from user where comment = '555' for update; begin;
3 insert user select 26,'666','666';
4 ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction
5 insert user select 31,'3131','3131';
6 ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction
7 insert user select 10,'100','100';
8 ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

Сяо Мин видит: «Ой, отпусти меня, что происходит?» Независимо от того, используете ли вы данные в диапазоне блокировки без промежутка в эксперименте 1 или данные в блокировке с промежутком, вы не можете использовать данные в блокировке с промежутком. Это добавляет блокировку таблицы?

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

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

4. Назад к аварии

4.1 Тупик

После того, как Сяомин закончил эксперимент, он, наконец, понял некоторые основные процедуры блокировки, но что это был за тупик, который появился в сети раньше?

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

Есть два пути выхода из тупика:

  1. Ожидание тайм-аута: Когда транзакция ждет тайм-аут и откатывает транзакцию, может быть выполнена другая транзакция, но это неэффективно, и будет время ожидания.Другая проблема в том, что если эта транзакция занимает большой вес, много данных было обновлено, но выполнен откат, что приведет к пустой трате ресурсов.
  2. График ожидания: График ожидания используется для описания отношения ожидания между транзакциями.Когда появляется этот график, цикл выглядит следующим образом:

Происходит откат.Вообще говоря, InnoDB выберет откат транзакций с меньшими весами, то есть транзакций с меньшей отменой.

4.2 Онлайн-вопросы

Когда Сяо Мин попал сюда, у него были все необходимые базовые навыки, поэтому он начал воспроизводить эту проблему в своей локальной таблице:

момент времени Транзакция А Транзакция Б
1 begin; begin;
2 delete from user where name = '777'; delete from user where name = '666';
3 insert user select 27,'777','777'; insert user select 26,'666','666';
4 ERROR 1213 (40001): Deadlock found when trying to get lock; try restarting transaction Query OK, 1 row affected (14.32 sec) Records: 1 Duplicates: 0 Warnings: 0

Видно, что транзакция A откатывается, а транзакция B выполняется успешно. Что именно происходило в каждый момент времени?

Момент времени 2: транзакция A удаляет данные с именем = '777' и должна добавить блокировку следующего ключа в индекс 777, но он не существует, поэтому добавляется только блокировка пробела между 555-999 и та же транзакция B также блокируется. Добавьте блокировку промежутка между 555-999. Замки Gap совместимы.

Момент времени 3: транзакция A выполняет операцию Insert и вставляет блокировку намерения первой, но между 555 и 999 имеется блокировка пробела. Из-за конфликта между блокировкой намерения вставки и блокировкой пробела транзакция A блокируется и ожидает транзакцию B. чтобы снять блокировку зазора. Точно так же транзакция B ожидает, пока транзакция A освободит блокировку разрыва. Итак, ожидание цикла A->B, B->A.

Момент времени 4: диспетчер транзакций решает откатить транзакцию A, и операция вставки транзакции B выполняется успешно.

4.3 Исправить ОШИБКУ

Эта проблема была наконец обнаружена Xiao Ming из-за блокировки пробела, и теперь нам нужно решить эту проблему.Причина этой проблемы в том, что есть блокировка пробела, поэтому давайте избавимся от нее:

  • Вариант 1: Уровень изоляции понижается до RC, и на уровне RC не будет добавлена ​​блокировка пробелов, поэтому проблем не будет, но на уровне RC будут фантомные чтения, а фиксируемые чтения разрушат изоляцию, так что этой схемы нет.
  • Решение 2: уровень изоляции повышен до сериализуемого.Сяомин обнаружил, что эта проблема не возникнет после тестирования.Однако на сериализуемом уровне производительность будет ниже и будет больше ожидания блокировки, что также не учитывается.
  • Вариант 3: изменить логику кода, не удалять его напрямую, изменить все данные на бизнес-логику, чтобы определить, какие из них обновлены, какие удалены, а какие добавлены, рабочая нагрузка немного больше, Сяомин написал логику прямого удаления просто чтобы не заниматься этими сложными вещами, поэтому эта программа рассматриваться не будет.
  • Вариант 4: Меньше логики кода модификации, перед удалением можно запросить через снапшоты (без блокировки), если запрос не дал результатов, он будет вставлен напрямую, если есть удаление через первичный ключ, в предыдущем разделе 3 Эксперимент 2 , через Уникальные индексы понижены до блокировок записи, поэтому блокировок пробелов нет.

Подумав об этом, Сяомин выбрал четвертый тип и немедленно починил его.Затем он вышел в интернет, чтобы понаблюдать и убедиться, что эта ошибка больше не появится.Теперь Сяомин, наконец, может спать спокойно.

4.4 Как предотвратить взаимоблокировку

Сяомин подытожил следующие моменты на основе базового обучения и обычного опыта:

  • Доступ к таблицам и строкам в фиксированном порядке. Перекрестный доступ чаще вызывает циклы ожидания транзакций.
  • Старайтесь избегать больших транзакций, чем больше блокировок ресурсов вы занимаете, тем легче вызвать взаимоблокировки. Рекомендуется разбивать его на небольшие сделки.
  • Понизьте уровень изоляции. Если бизнес это позволяет (это также проанализировано в 4.3 выше, некоторые бизнесы не разрешены), это также хороший выбор для снижения уровня изоляции.Например, изменение уровня изоляции с RR на RC может избежать многих взаимоблокировок, вызванных щелевые замки. .
  • Добавьте в таблицу разумные индексы. Чтобы предотвратить блокировку таблицы без индексов, вероятность взаимоблокировок резко возрастет.

Наконец

Из-за ограниченного места многие вещи не могут быть представлены.Если вам интересно, вы можете прочитать главу 6 "Mysql Technology Insider - InnoDB Engine" иMaster He's MySQL Анализ обработки блокировок. Сам автор ограничен, если есть ошибки прошу поправить.

Наконец, эта статья была включена в JGrowing, всеобъемлющий и отличный маршрут изучения Java, совместно созданный сообществом.Если вы хотите участвовать в обслуживании проектов с открытым исходным кодом, вы можете создать его вместе.Адрес github:GitHub.com/Java растет…Пожалуйста, дайте мне маленькую звезду.

Если вы считаете, что в этой статье есть статьи для вас, вы можете подписаться на мой технический паблик Ваше внимание и пересылка - самая большая поддержка для меня, O(∩_∩)O