Spec-Zone .ru
спецификации, руководства, описания, API

13.1.17.1. CREATE TABLE ...SELECT Синтаксис

Можно составить одну таблицу от другого, добавляя a SELECT оператор в конце CREATE TABLE оператор:

CREATE TABLE new_tbl [AS] SELECT * FROM orig_tbl;

MySQL создает новые столбцы для всех элементов в SELECT. Например:

mysql> CREATE TABLE test (a INT NOT NULL
        AUTO_INCREMENT,    ->        PRIMARY KEY (a), KEY(b))    ->        ENGINE=MyISAM SELECT b,c FROM test2;

Это создает a MyISAM таблица с тремя столбцами, a, b, и c. ENGINE опция является частью CREATE TABLE оператор, и не должен использоваться после SELECT; это привело бы к синтаксической ошибке. То же самое является истиной для другого CREATE TABLE опции такой как CHARSET.

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

mysql> SELECT * FROM foo;+---+| n |+---+| 1 |+---+mysql> CREATE TABLE bar (m INT) SELECT n FROM foo;Query OK, 1 row affected (0.02 sec)Records: 1  Duplicates: 0  Warnings: 0mysql> SELECT * FROM bar;+------+---+| m    | n |+------+---+| NULL | 1 |+------+---+1 row in set (0.00 sec)

Для каждой строки в таблице foo, строка вставляется в bar со значениями от foo и значения по умолчанию для новых столбцов.

В таблице, следующей CREATE TABLE ... SELECT, столбцы, названные только в CREATE TABLE часть на первом месте. Столбцы, названные в обеих частях или только в SELECT часть, прибывшая после этого. Тип данных SELECT столбцы могут быть переопределены, также определяя столбец в CREATE TABLE часть.

Если какие-либо ошибки происходят, копируя данные в таблицу, они автоматически отбрасываются и не создаются.

Можно предшествовать SELECT IGNORE или REPLACE указать, как обработать строки тот двойной уникальный ключ значения. С IGNORE, отбрасываются новые строки, которые копируют существующую строку на значении уникального ключа. С REPLACE, новые строки заменяют строки, у которых есть то же самое значение уникального ключа. Если ни один IGNORE ни REPLACE определяется, двойной результат значений уникального ключа по ошибке.

Поскольку упорядочивание строк в базовом SELECT операторы не могут всегда определяться, CREATE TABLE ... IGNORE SELECT и CREATE TABLE ... REPLACE SELECT операторы в MySQL 5.6.4 и позже отмечаются как опасные для основанной на операторе репликации. С этим изменением такие операторы производят предупреждение в журнале при использовании основанного на операторе режима и регистрируются, используя основанный на строке формат при использовании MIXED режим. См. также Раздел 16.1.2.1, "Преимущества и Недостатки Основанной на операторе и Построчной репликации".

CREATE TABLE ... SELECT автоматически не создает любой индексирует для Вас. Это делается преднамеренно, чтобы сделать оператор настолько гибким насколько возможно. Если Вы хотите иметь, индексирует в составленной таблице, следует определить их перед SELECT оператор:

mysql> CREATE TABLE bar (UNIQUE (n)) SELECT n FROM
        foo;

Некоторое преобразование типов данных могло бы произойти. Например, AUTO_INCREMENT атрибут не сохраняется, и VARCHAR столбцы могут стать CHAR столбцы. Переобученные атрибуты NULL (или NOT NULL) и, для тех столбцов, у которых есть они, CHARACTER SET, COLLATION, COMMENT, и DEFAULT пункт.

Составляя таблицу с CREATE TABLE ... SELECT, удостоверьтесь, что исказили любые вызовы функции или выражения в запросе. Если Вы не делаете, CREATE оператор мог бы перестать работать или привести к нежелательным именам столбцов.

CREATE TABLE artists_and_works  SELECT artist.name, COUNT(work.artist_id) AS number_of_works  FROM artist LEFT JOIN work ON artist.id = work.artist_id  GROUP BY artist.id;

Можно также явно определить тип данных для сгенерированного столбца:

CREATE TABLE foo (a TINYINT NOT NULL) SELECT b+1 AS a FROM bar;

Для CREATE TABLE ... SELECT, если IF NOT EXISTS дается и целевая таблица уже существует, результатом является зависимая версия. Перед MySQL 5.5.6 MySQL обрабатывает оператор следующим образом:

Следующий пример иллюстрирует IF NOT EXISTS обработка:

mysql> CREATE TABLE t1 (i1 INT DEFAULT 0, i2 INT, i3
        INT, i4 INT);Query OK, 0 rows affected (0.05 sec)mysql> CREATE
        TABLE IF NOT EXISTS t1 (c1 CHAR(10)) SELECT 1, 2;Query OK, 1 row affected, 1 warning (0.01 sec)Records: 1  Duplicates: 0  Warnings: 0mysql> SELECT * FROM t1;+------+------+------+------+| i1   | i2   | i3   | i4   |+------+------+------+------+|    0 | NULL |    1 |    2 |+------+------+------+------+1 row in set (0.00 sec)

С MySQL 5.5.6, обработки CREATE TABLE IF NOT EXISTS ... SELECT операторы были изменены для случая, что целевая таблица уже существует. Это изменение также включает изменение в MySQL 5.1, начинающийся 5.1.51.

Это изменение означает что, для предыдущего примера, CREATE TABLE IF NOT EXISTS ... SELECT оператор ничего не вставляет в целевую таблицу с MySQL 5.5.6.

Это изменение в обработке IF NOT EXISTS результаты в несовместимости для основанной на операторе репликации от ведущего устройства MySQL 5.1 с исходным поведением и ведомого устройства MySQL 5.5 с новым поведением. Предположите это CREATE TABLE IF NOT EXISTS ... SELECT выполняется на ведущем устройстве, и целевая таблица существует. Результат состоит в том, что строки вставляются на ведущем устройстве, но не на ведомом устройстве. (У построчной репликации нет этой проблемы.)

Решать эту проблему, основанное на операторе двоичное журналирование для CREATE TABLE IF NOT EXISTS ... SELECT изменяется в MySQL 5.1 с 5.1.51:

Это изменение обеспечивает прямую совместимость для основанной на операторе репликации от MySQL 5.1 до 5.5, потому что, когда целевая таблица существует, строки будут вставлены и на ведущем устройстве и на ведомом устройстве. Чтобы использовать в своих интересах эту меру по совместимости, 5.1 серверов должны быть по крайней мере 5.1.51, и 5.5 серверов должны быть по крайней мере 5.5.6.

Чтобы обновить существующее 5.1 к 5.5 сценарий репликации, обновите ведущее устройство сначала до 5.1.51 или выше. Отметьте, что это отличается от обычного совета обновления репликации обновления ведомого устройства сначала.

Обходное решение для приложений, которые хотят достигнуть исходного эффекта (строки, вставленные независимо от того, ли целевая таблица существует), должно использовать CREATE TABLE IF NOT EXISTS и INSERT ... SELECT операторы, а не CREATE TABLE IF NOT EXISTS ... SELECT операторы.

Наряду с изменением, только описанным, было произведено следующее связанное изменение: Ранее, если существующее представление назвали как целевая таблица для CREATE TABLE IF NOT EXISTS ... SELECT, строки были вставлены в базовую базовую таблицу, и оператор был записан двоичному журналу. С MySQL 5.1.51 и 5.5.6 ничто не вставляется или регистрируется.

Чтобы гарантировать, что двоичный журнал может использоваться, чтобы воссоздать исходные таблицы, MySQL не разрешает параллельные вставки во время CREATE TABLE ... SELECT.

Важный

Невозможно использовать FOR UPDATE как часть SELECT в операторе такой как CREATE TABLE new_table SELECT ... FROM old_table .... Если Вы пытаетесь сделать так, сбои оператора. Это представляет изменение в поведении от MySQL 5.5 и ранее, который разрешал CREATE TABLE ... SELECT операторы, чтобы произвести изменения в таблицах кроме составленной таблицы.

У этого изменения могут также быть импликации для основанной на операторе репликации от ведущего устройства старшего возраста к MySQL 5.6 или более нового ведомого устройства. См. Раздел 16.4.1.5, "Репликация CREATE TABLE ... SELECT Операторы", для получения дополнительной информации.