15.2.7 Оператор INSERT
INSERT [LOW_PRIORITY | DELAYED | HIGH_PRIORITY] [IGNORE]
[INTO] tbl_name
[PARTITION (partition_name [, partition_name] ...)]
[(col_name [, col_name] ...)]
{ {VALUES | VALUE} (value_list) [, (value_list)] ... }
[AS row_alias[(col_alias [, col_alias] ...)]]
[ON DUPLICATE KEY UPDATE assignment_list]
INSERT [LOW_PRIORITY | DELAYED | HIGH_PRIORITY] [IGNORE]
[INTO] tbl_name
[PARTITION (partition_name [, partition_name] ...)]
SET assignment_list
[AS row_alias[(col_alias [, col_alias] ...)]]
[ON DUPLICATE KEY UPDATE assignment_list]
INSERT [LOW_PRIORITY | HIGH_PRIORITY] [IGNORE]
[INTO] tbl_name
[PARTITION (partition_name [, partition_name] ...)]
[(col_name [, col_name] ...)]
{ SELECT ...
| TABLE table_name
| VALUES row_constructor_list
}
[ON DUPLICATE KEY UPDATE assignment_list]
value:
{expr | DEFAULT}
value_list:
value [, value] ...
row_constructor_list:
ROW(value_list)[, ROW(value_list)][, ...]
assignment:
col_name =
value
| [row_alias.]col_name
| [tbl_name.]col_name
| [row_alias.]col_alias
assignment_list:
assignment [, assignment] ...
INSERT добавляет новые строки в существующую таблицу. INSERT
... VALUES, INSERT ... VALUES
ROW() и INSERT ... SET формы оператора добавляют строки, основанные на явно указанных значениях. INSERT
... SELECT форма добавляет строки, выбранные из другой таблицы или таблиц. Также можно использовать INSERT ... TABLE для добавления строк из одной таблицы. INSERT с предложением ON
DUPLICATE KEY UPDATE позволяет обновлять существующие строки, если вставка строки приведёт к дублированию значения в индексе UNIQUE или PRIMARY KEY. Псевдоним строки с одним или несколькими необязательными псевдонимами столбцов может быть использован с ON DUPLICATE KEY UPDATE для ссылки на вставляемую строку.
Дополнительную информацию об INSERT ...
SELECT и INSERT ... ON
DUPLICATE KEY UPDATE см. в разделе 15.2.7.1, «Оператор INSERT ... SELECT» и разделе 15.2.7.2, «Оператор INSERT ... ON DUPLICATE KEY UPDATE».
В MySQL 9.2 ключевое слово DELAYED поддерживается, но игнорируется сервером. Причины этого см. в разделе 15.2.7.3, «Оператор INSERT DELAYED».
Для вставки в таблицу требуется привилегия INSERT для этой таблицы. Если используется предложение ON DUPLICATE KEY UPDATE и дублирование ключа приводит к выполнению UPDATE вместо этого, оператор требует привилегии UPDATE для обновляемых столбцов. Для столбцов, которые считываются, но не изменяются, требуется только привилегия SELECT (например, для столбца, упоминаемого только в правой части присваивания col_name=expr в предложении ON DUPLICATE KEY UPDATE).
При вставке в разнесённую таблицу можно контролировать, какие разделы и подразделы принимают новые строки. Предложение PARTITION принимает список разделённых запятыми имён одного или нескольких разделов или подразделов (или обоих) таблицы. Если какая-либо из строк, которые должны быть вставлены заданным оператором INSERT, не соответствует одному из перечисленных разделов, оператор INSERT завершается с ошибкой Найдена строка, не соответствующая заданному набору разделов. Дополнительную информацию и примеры см. в разделе 26.5, «Выбор раздела».
tbl_name — таблица, в которую должны быть вставлены строки. Укажите столбцы, для которых оператор предоставляет значения следующим образом:
Укажите список разделённых запятыми имён столбцов в скобках после имени таблицы. В этом случае значение для каждого указанного столбца должно быть предоставлено списком
VALUES, спискомVALUES ROW()или операторомSELECT. Для формыINSERT TABLEколичество столбцов в исходной таблице должно соответствовать количеству вставляемых столбцов.Если вы не указываете список имён столбцов для оператора
INSERT ... VALUESилиINSERT ... SELECT, значения для каждого столбца таблицы должны быть предоставлены спискомVALUES, операторомSELECTили операторомTABLE. Если вы не знаете порядок столбцов в таблице, используйтеDESCRIBEдля его определения.tbl_nameПредложение
SETявно указывает столбцы по имени вместе со значением, которое им следует присвоить.
Значения столбцов могут быть заданы несколькими способами:
-
Если режим строгой SQL-совместимости не включён, любой столбец, которому не задано явное значение, устанавливается в его значение по умолчанию (явное или неявное). Например, если вы указываете список столбцов, который не называет все столбцы в таблице, для неуказанных столбцов устанавливаются значения по умолчанию. Присваивание значений по умолчанию описано в разделе 13.6, «Значения по умолчанию типов данных».
Если режим строгой SQL-совместимости включён, оператор
INSERTгенерирует ошибку, если не указывает явное значение для каждого столбца, не имеющего значения по умолчанию. См. раздел 7.1.11, «Режимы SQL сервера». -
Если список столбцов и список
VALUESпусты, операторINSERTсоздаёт строку, в которой каждый столбец устанавливается в своё значение по умолчанию:INSERT INTO
tbl_name() VALUES();Если режим строгой SQL-совместимости не включён, MySQL использует неявное значение по умолчанию для любого столбца, не имеющего явным образом определённого значения по умолчанию. Если режим строгой SQL-совместимости включён, появляется ошибка, если какой-либо столбец не имеет значения по умолчанию.
Используйте ключевое слово
DEFAULT, чтобы явно установить столбец в его значение по умолчанию. Это упрощает написание операторовINSERT, присваивающих значения всем, кроме нескольких столбцов, так как позволяет избежать составления неполного спискаVALUES, не содержащего значения для каждого столбца таблицы. В противном случае необходимо указать список имён столбцов, соответствующих каждому значению в спискеVALUES.-
Если сгенерированный столбец вставляется явно, единственное разрешённое значение —
DEFAULT. Подробности о сгенерированных столбцах см. в разделе 15.1.21.8, «CREATE TABLE и сгенерированные столбцы». В выражениях можно использовать
DEFAULT(для получения значения по умолчанию столбцаcol_name)col_name.Преобразование типов выражения
expr, предоставляющего значение столбца, может произойти, если тип данных выражения не соответствует типу данных столбца. Преобразование заданного значения может привести к разным вставляемым значениям в зависимости от типа столбца. Например, вставка строки'1999.0e-2'в столбецINT,FLOAT,DECIMAL(10,6)илиYEARвставляет соответственно значение1999,19.9921,19.992100или1999. Сохранённое значение в столбцахINTиYEARравно1999, так как преобразование строки в число рассматривает только начальную часть строки, которая может считаться допустимым целым числом или годом. Для столбцовFLOATиDECIMALпреобразование строки в число рассматривает всю строку как допустимое числовое значение.-
Выражение
exprможет ссылаться на любой столбец, который был установлен ранее в списке значений. Например, это возможно, так как значение дляcol2относится кcol1, которому ранее было присвоено значение:INSERT INTO
tbl_name(col1,col2) VALUES(15,col1*2);Но следующее не является допустимым, так как значение для
col1относится кcol2, которое присваивается послеcol1:INSERT INTO
tbl_name(col1,col2) VALUES(col2*2,15);Исключение возникает для столбцов, содержащих значения
AUTO_INCREMENT. Поскольку значенияAUTO_INCREMENTгенерируются после других присваиваний значений, любая ссылка на столбецAUTO_INCREMENTв присваивании возвращает значение0.
Операторы INSERT с использованием синтаксиса VALUES могут вставлять несколько строк. Для этого включите несколько списков разделённых запятыми значений столбцов, заключённых в скобки и разделённых запятыми. Пример:
INSERT INTO tbl_name (a,b,c)
VALUES(1,2,3), (4,5,6), (7,8,9);
Каждый список значений должен содержать ровно столько значений, сколько требуется для вставки в строку. Следующее утверждение некорректно, так как оно содержит один список из девяти значений, а не три списка по три значения каждый:
INSERT INTO tbl_name (a,b,c) VALUES(1,2,3,4,5,6,7,8,9);
VALUE является синонимом для VALUES в данном контексте. Ни одно из них не подразумевает ничего о количестве списков значений или количестве значений в каждом списке. Оба могут использоваться, как при наличии одного списка значений, так и при наличии нескольких списков, независимо от количества значений в каждом списке.
Заявления INSERT с использованием синтаксиса VALUES также могут вставлять несколько строк. В этом случае каждый список значений должен быть заключен в ROW() (конструктор строки), как показано ниже:
INSERT INTO tbl_name (a,b,c)
VALUES ROW(1,2,3), ROW(4,5,6), ROW(7,8,9);
Значение affected-rows для заявления INSERT может быть получено с помощью SQL-функции ROW_COUNT() или функции C API. См. раздел 14.15 «Функции информации», и .
Если вы используете заявление INSERT или INSERT ...
SELECT с несколькими списками значений, или INSERT ...
SELECT или INSERT ... TABLE, заявление возвращает строку информации в следующем формате:
Records: N1 Duplicates: N2 Warnings: N3
Если вы используете C API, строку информации можно получить, вызвав функцию . См. .
Records указывает количество обработанных строк заявлением. (Это не обязательно количество фактически вставленных строк, потому что Duplicates может быть отличным от нуля.) Duplicates указывает количество строк, которые не могли быть вставлены, потому что они дублировали значение какого-либо существующего уникального индекса. Warnings указывает количество попыток вставить значения столбцов, которые были проблемными. Предупреждения могут возникнуть в следующих условиях:
Вставка
NULLв столбец, который был объявленNOT NULL. Для многострочных заявлений INSERT илиINSERT INTO ... SELECTзаявлений столбец устанавливается в неявное значение по умолчанию для типа данных столбца. Это0для числовых типов, пустая строка ('') для строковых типов и значение «ноль» для типов дат и времени.INSERT INTO ... SELECTобрабатываются так же, как и многострочные вставки, поскольку сервер не проверяет результат набора изSELECTдля проверки, возвращает ли он одну строку. (Для однострочногоINSERTпредупреждение не возникает, когдаNULLвставляется в столбецNOT NULL. Вместо этого заявление завершается ошибкой.)Установка числового столбца на значение, выходящее за пределы диапазона столбца. Значение усекается до ближайшей точки диапазона.
Назначение значения, такого как
'10.34 a', числовому столбцу. Прицепленные нечисловые символы удаляются, и оставшаяся числовая часть вставляется. Если в строковом значении нет начальной числовой части, столбец устанавливается в0.Вставка строки в строковый столбец (
CHAR,VARCHAR,TEXTилиBLOB), превышающей максимальную длину столбца. Значение усекается до максимальной длины столбца.Вставка значения в столбец даты или времени, которое не является допустимым для типа данных. Столбец устанавливается на соответствующее нулевое значение для типа.
-
Для
INSERTпримеров, включающих значения столбцовAUTO_INCREMENT, см. раздел 5.6.9 «Использование AUTO_INCREMENT».Если
INSERTвставляет строку в таблицу, имеющую столбецAUTO_INCREMENT, вы можете найти значение, использованное для этого столбца, с помощью SQL-функцииLAST_INSERT_ID()или функции C API.ПримечаниеЭти две функции не всегда ведут себя одинаково. Поведение
INSERTзаявлений относительно столбцовAUTO_INCREMENTобсуждается далее в разделе 14.15 «Функции информации», и .
Заявление INSERT поддерживает следующие модификаторы:
-
Если вы используете модификатор
LOW_PRIORITY, выполнениеINSERTоткладывается до тех пор, пока другие клиенты не перестанут читать из таблицы. Это включает других клиентов, которые начали чтение, пока существующие клиенты читают, и пока запросINSERT LOW_PRIORITYожидает. Таким образом, клиент, который выполняет запросINSERT LOW_PRIORITY, может ждать очень долго.LOW_PRIORITYвлияет только на движки хранения, использующие только блокировку на уровне таблицы (например,MyISAM,MEMORYиMERGE).ПримечаниеLOW_PRIORITYобычно не следует использовать с таблицамиMyISAM, так как это отключает одновременные вставки. См. Раздел 10.11.3, «Одновременные вставки». -
Если вы укажете
HIGH_PRIORITY, это переопределит действие параметра--low-priority-updates, если сервер был запущен с этим параметром. Также это приведет к тому, что одновременные вставки не будут использоваться. См. Раздел 10.11.3, «Одновременные вставки».HIGH_PRIORITYвлияет только на движки хранения, использующие только блокировку на уровне таблицы (например,MyISAM,MEMORYиMERGE). -
Если вы используете модификатор
IGNORE, игнорируются ошибки, которые возникают при выполнении запросаINSERT. Например, безIGNOREстрока, дублирующая существующийUNIQUEиндекс илиPRIMARY KEYзначение в таблице, вызывает ошибку дублирования ключа, и запрос отменяется. СIGNOREстрока отбрасывается, и ошибка не возникает. Вместо этого игнорируемые ошибки генерируют предупреждения.IGNOREимеет аналогичный эффект на вставки в разнесённые таблицы, где не найдена ни одна секция, соответствующая заданному значению. БезIGNOREтакие запросыINSERTотменяются с ошибкой. Когда используетсяINSERT IGNORE, операция вставки безмолвно завершается неудачей для строк, содержащих несовпадающее значение, но вставляет строки, которые совпадают. Пример см. в Разделе 26.2.2, «Разбиение списка».Преобразования данных, которые вызвали бы ошибки, отменяют запрос, если не указан
IGNORE. СIGNOREнекорректные значения корректируются до ближайших значений и вставляются; генерируются предупреждения, но запрос не прерывается. Вы можете определить с помощью функции API C, сколько строк было фактически вставлено в таблицу.Дополнительную информацию см. в Разделе «Влияние IGNORE на выполнение запроса».
Вы можете использовать
REPLACEвместоINSERTдля перезаписи старых строк.REPLACEявляется аналогомINSERT IGNOREпри обработке новых строк, которые содержат уникальные значения ключа, дублирующие старые строки: новые строки заменяют старые строки, а не отбрасываются. См. Раздел 15.2.12, «Запрос REPLACE». -
Если вы укажете
ON DUPLICATE KEY UPDATE, и при вставке строки произойдёт дублирование значения вUNIQUEиндексе илиPRIMARY KEY, произойдётUPDATEстарой строки. Значение affected-rows для каждой строки равно 1, если строка вставляется как новая, 2, если существующая строка обновляется, и 0, если существующая строка устанавливается в её текущие значения. Если вы укажете флагCLIENT_FOUND_ROWSв функции API C при подключении к mysqld, значение affected-rows будет равно 1 (а не 0), если существующая строка устанавливается в её текущие значения. См. Раздел 15.2.7.2, «Запрос INSERT ... ON DUPLICATE KEY UPDATE». -
INSERT DELAYEDустарел в MySQL 5.6 и будет в конечном итоге удалён. В MySQL 9.2 модификаторDELAYEDпринимается, но игнорируется. ИспользуйтеINSERT(безDELAYED) вместо него. См. Раздел 15.2.7.3, «Запрос INSERT DELAYED».
© 2025 Oracle
Licensed under the GPLv2 License.