Curso de MySQL
Consultas, lista de correo 'C++ Con Clase' 'MySQL Con Clase' página de entrada Tabla de contenido Contactar con Webmaster
Curso Sentencias Funciones API C

SQL

Sentencias

ALTER TABLE ANALYZE TABLE BACKUP TABLE BEGIN BEGIN WORK CHECK TABLE CHECKSUM TABLE COMMIT CREATE DATABASE CREATE USER DELETE DESCRIBE DO DROP DATABASE DROP INDEX DROP TABLE DROP USER FLUSH GRANT HANDLER INSERT INSERT ... SELECT INSERT DELAYED JOIN KILL LOAD DATA LOCK TABLES OPTIMIZE TABLE RENAME TABLE REPAIR TABLE REPLACE RESET REVOKE ROLLBACK SELECT SET SET TRANSACTION SHOW SHOW CHARACTER SET SHOW COLLATION SHOW COLUMNS SHOW CREATE DATABASE SHOW CREATE TABLE SHOW CREATE VIEW SHOW DATABASES SHOW ENGINES SHOW ERRORS SHOW GRANTS SHOW INDEX SHOW INNODB STATUS SHOW KEYS SHOW LOGS SHOW PRIVILEGES SHOW PROCESSLIST SHOW STATUS SHOW TABLE STATUS SHOW TABLES SHOW VARIABLES SHOW WARNINGS START TRANSACTION TRUNCATE UNION UNLOCK TABLES UPDATE USE

CREATE TABLE

CREATE [TEMPORARY] TABLE [IF NOT EXISTS] tbl_name 
  [(definición_create,...)]
  [opciones_tabla] [sentencia_select]

O

CREATE [TEMPORARY] TABLE [IF NOT EXISTS] tbl_name 
   [(] LIKE viejo_tbl_name [)];

Sintaxis de definición_create:

    definición_columnas
  | [CONSTRAINT [símbolo]] PRIMARY KEY (index_nombre_col,...)
  | KEY [nombre_index] (nombre_col_index,...)
  | INDEX [nombre_index] (nombre_col_index,...)
  | [CONSTRAINT [símbolo]] UNIQUE [INDEX] 
       [nombre_index] [tipo_index] (nombre_col_index,...)
  | [FULLTEXT|SPATIAL] [INDEX] [nombre_index] (nombre_col_index,...)
  | [CONSTRAINT [símbolo]] FOREIGN KEY 
       [nombre_index] (nombre_col_index,...) [definición_referencia]
  | CHECK (expr)

Sintaxis de definición_columnas:

    nombre_col tipo [NOT NULL | NULL] [DEFAULT valor_por_defecto] 
        [AUTO_INCREMENT] [[PRIMARY] KEY] [COMMENT 'string'] 
        [definición_referencia]

Sintaxis de tipo:

    TINYINT[(longitud)] [UNSIGNED] [ZEROFILL]
  | SMALLINT[(longitud)] [UNSIGNED] [ZEROFILL]
  | MEDIUMINT[(longitud)] [UNSIGNED] [ZEROFILL]
  | INT[(longitud)] [UNSIGNED] [ZEROFILL]
  | INTEGER[(longitud)] [UNSIGNED] [ZEROFILL]
  | BIGINT[(longitud)] [UNSIGNED] [ZEROFILL]
  | REAL[(longitud,decimales)] [UNSIGNED] [ZEROFILL]
  | DOUBLE[(longitud,decimales)] [UNSIGNED] [ZEROFILL]
  | FLOAT[(longitud,decimales)] [UNSIGNED] [ZEROFILL]
  | DECIMAL(longitud,decimales) [UNSIGNED] [ZEROFILL]
  | NUMERIC(longitud,decimales) [UNSIGNED] [ZEROFILL]
  | DATE
  | TIME
  | TIMESTAMP
  | DATETIME
  | CHAR(longitud) [BINARY | ASCII | UNICODE]
  | VARCHAR(longitud) [BINARY]
  | TINYBLOB
  | BLOB
  | MEDIUMBLOB
  | LONGBLOB
  | TINYTEXT
  | TEXT
  | MEDIUMTEXT
  | LONGTEXT
  | ENUM(valor1,valor2,valor3,...)
  | SET(valor1,valor2,valor3,...)
  | tipo_spatial

Sintaxis de nombre_col_index:

        nombre_col [(longitud)] [ASC | DESC]

Sintaxis de definición_referencia:

        REFERENCES nombre_tbl [(nombre_col_index,...)]
                   [MATCH FULL | MATCH PARTIAL | MATCH SIMPLE]
                   [ON DELETE opción_referencia]
                   [ON UPDATE opción_referencia]

Sintaxis de opción_referencia:

        RESTRICT | CASCADE | SET NULL | NO ACTION | SET DEFAULT

Sintaxis de opciones_tabla:

 opción_tabla [opción_tabla] ...

Sintaxis de opción_tabla:

    {ENGINE|TYPE} = {BDB|HEAP|ISAM|InnoDB|MERGE|MRG_MYISAM|MYISAM }
  | AUTO_INCREMENT = valor
  | AVG_ROW_LENGTH = valor
  | CHECKSUM = {0 | 1}
  | COMMENT = 'cadena'
  | MAX_ROWS = valor
  | MIN_ROWS = valor
  | PACK_KEYS = {0 | 1 | DEFAULT}
  | PASSWORD = 'cadena'
  | DELAY_KEY_WRITE = {0 | 1}
  | ROW_FORMAT = { DEFAULT|DYNAMIC|FIXED|COMPRESSED|REDUNTANT|COMPACT}
  | RAID_TYPE = { 1 | STRIPED | RAID0 } 
       RAID_CHUNKS=valor
       RAID_CHUNKSIZE=valor
  | UNION = (nombre_tabla,[nombre_tabla...])
  | INSERT_METHOD = { NO | FIRST | LAST }
  | DATA DIRECTORY = 'camino de directorio absoluto'
  | INDEX DIRECTORY = 'camino de directorio absoluto'
  | [DEFAULT] CHARACTER SET nombre_conjunto_caracteres [COLLATE nombre_cotejo]

Sintaxis de sentencia_select:

    [IGNORE | REPLACE] [AS] SELECT ...     (Alguna sentencia select legal)

CREATE TABLE crea una tabla con el nombre dado. Se debe poseer el privilegio CREATE para la tabla.

Las reglas para nombres válidos de tablas se pueden ver aquí. Por defecto, la tabla se crea en la base de datos actual. Se producirá un error si la tabla ya existe, si no hay una base de datos actual o si la base de datos no existe.

En versiones de MySQL 3.22 y posteriores, el nombre de la tabla se puede especificar como db_name.tbl_name para la creación de la tabla en una base de datos específica. Esto funciona aunque no exista una base de datos seleccionada. Si se escribe el nombre de la tabla entre comillas, el nombre de la base de datos y el de la tabla se deben entrecomillar separadamente. Por ejemplo, `midb`.`mitabla` es legal, pero `midb.mitabla` no lo es.

Desde la versión 3.23 de MySQL se puede usar la palabra clave TEMPORARY cuando se quiere crear una tabla. La tabla temporal sólo es visible para la conexión actual, y será borrada automáticamente cuando se cierre la conexión. Esto significa que dos conexiones diferentes pueden usar simultaneamente el mismo nombre para una tabla temporal sin conflictos entre ellas o con una tabla existente con el mismo nombre. (La tabla existente se ocultará hasta que la tabla temporal sea borrada). Desde MySQL 4.0.2 se debe tener el privilegio CREATE TEMPORARY TABLES para que sea posible crear tablas temporales.

Desde la versión 3.23 de MySQL se puede usar IF NOT EXISTS de modo que no se obtiene un error si la tabla ya existe. No se hace verificación de si la tabla existente tiene una estructura idéntica a la indicada por la sentecia CREATE TABLE.

Cada tabla tbl_name se representa mediante algunos ficheros en el directorio de la base de datos. En el caso de tablas de tipo MyISAM se tendrá:

Fichero Propósito
tbl_name.frm Fichero de definición de formato de tabla
tbl_name.MYD Fichero de datos
tbl_name.MYI Fichero de índices

En la documentación de MySQL es posible encontrar información sobre el modo en que cada motor de almacenamiento crea los ficheros que representan las tablas.

Para detalles sobre tipos de columnas ver el capítulo 5.

De momento no hemos incluido información sobre las extensiones espaciales de MySQL (spatial).

La parte opciones_tabla de CREATE TABLE sólo están disponibles desde MySQL 3.23.

Las opciones ENGINE y TYPE especifican el motor de almacenamiento para la tabla. ENGINE se añadió en MySQL 4.0.18 (para 4.0) y 4.1.2 (para 4.1). Esta es la opción aconsejada desde esas versiones, y TYPE queda desaconsejada. TYPE será soportada a lo largo de la serie 4.x series, pero será eliminada en MySQL 5.1.

Las opciones ENGINE y TYPE pueden tomar los valores siguientes:

Motor de almacenamiento Descripción
BDB Tablas de transacción segura con bloqueo de página.
BerkeleyDB Alias para BDB.
HEAP Los datos para esta tabla sólo se almacenan en memoria.
ISAM El motor de almacenamoento original de MySQL.
InnoDB Tablas de transacción segura con bloqueo de fila y claves foráneas.
MEMORY Alias para HEAP.
MERGE Una colección de tablas MyISAM usadas como una tabla.
MRG_MyISAM Un alias para MERGE.
MyISAM El nuevo motor binario de almacenamiento portable que reemplaza a ISAM.

Si se especifica un tipo de tabla, y ese tipo particular no está disponible, MySQL usará el tipo MyISAM. Por ejemplo, si la definición de la tabla incluye la opción ENGINE=BDB pero el servidor MySQL no soporta tablas BDB, la tabla se creará como una tabla MyISAM. Esto hace posible tener un sistema de réplica donde se tienen tablas operativas en el maestro pero las tablas creadas en el esclavo no son operativas (para obtener mayor velocidad). En MySQL 4.1.1 se obtiene un aviso si el tipo de tabla especificado no es aceptable.

Las otras opciones de tabla se usan para optimizar el comportamiento de la tabla. En la mayoría de los casos, no se tendrá que especificar ninguna de ellas. Las opciones trabajan con todos los tipos de tabla, salvo que se indique otra cosa:

Option Descripción
AUTO_INCREMENT El valor inicial AUTO_INCREMENT que se quiere seleccionar para la tabla. Sólo funciona en tablas MyISAM. Para poner el primer valor de un auto-incrementado para una tabla InnoDB, insertar una fila vacía con un valor una unidad menor, y después borrarla.
AVG_ROW_LENGTH Una aproximación de la longitud media de fila de la tabla. Sólo se necesita esto para tablas largas con tamaño de registro variable. When you create a MyISAM table, MySQL uses the product of the MAX_ROWS and AVG_ROW_LENGTH options to decide how big the resulting table will be. If you don't specify either option, the maximum size for a table will be 4GB (or 2GB if your operating system only supports 2GB tables). The reason for this is just to keep down the pointer sizes to make the index smaller and faster if you don't really need big files. If you want all your tables to be able to grow above the 4GB limit and are willing to have your smaller tables slightly slower and larger than necessary, you may increase the default pointer size by setting the myisam_data_pointer_size system variable, which was added in MySQL 4.1.2.
CHECKSUM Ponerlo a 1 si se quiere que MySQL mantenga un checksum para todas las filas (es decir, un checksum que MySQL actualiza automáticamente cuando la tabla cambia. Esto hace la tabla un poco más lenta al actualizar, pero hace más sencillo localizar tablas corruptas. La sentencia CHECKSUM TABLE devuelve el valor del checksum. (Sólo MyISAM).
COMMENT Un comentario de 60 caracteres para la tabla.
MAX_ROWS Número máximo de filas que se planea almacenar en la tabla.
MIN_ROWS Mínimo número de filas que se planea almacenar en la tabla.
PACK_KEYS Ponerlo a 1 si se quiere tener índices más pequeños. Esto normalmente hace que las actualizaciones sean más lentas y las lecturas más rápidas. Ponerlo a 0 desactiva cualquier empaquetado de claves. Ponerlo a DEFAULT (MySQL 4.0) indica al motor de almacenamiento que sólo empaquete columnas CHAR/VARCHAR largas. (Sólo MyISAM y ISAM). Si no se usa PACK_KEYS, por defecto sólo se empaquetan cadenas, no números. Si se usa PACK_KEYS=1, los números serán empaquetados también. Cuando se empaquetan claves de números binarios, MySQL usa compresión con prefijo:
  • Cada clave necesita un byte extra para indicar cuantos bytes de la clave anterior son iguales en la siguiente.
  • El puntero a la fila se almacena guardando primero el byte de mayor peso directamente después de la clave, para mejorar la compresión.
Esto significa que si existen muchas claves iguales en dos filas consecutivas, todas las claves "iguales" que sigan generalmente sólo necesitarán dos bytes (incluyendo el puntero a la fila). Comparar esto con el caso corriente, donde las claves siguientes tendrán tamaño_almacenamiento_clave + tamaño_puntero (donde el tamaño del puntero normalmente es 4). Por otra parte, sólo se obtendrá un gran beneficio de la compresión prefija si hay muchos números que sean iguales. Si todas las claves son totalmente distintas, se usará un byte más por clave, si la clave no es una que pueda tener valores NULL. (En ese caso, la longitud de la clave empaquetada será almacenada en el mismo byte que se usa para marcar si la clave es NULL.)
PASSWORD Encripta el fichero `.frm' con un password. Esta opción no hace nada en la versión estándar de MySQL.
DELAY_KEY_WRITE Poner esto a 1 si se quiere posponer la actualización de la tabla hasta que sea cerrada (sólo MyISAM).
ROW_FORMAT Define cómo deben almacenarse las filas. Actualmente esta opción sólo funciona con tablas MyISAM. El valor de la opción puede ser DYNAMIC o FIXED para formatos de fila estático o de longitud variable.
RAID_TYPE La opción RAID_TYPE permite exceder el límite de 2G/4G para un fichero de datos MyISAM (no el fichero de índice) en sistemas operativos que no soportan ficheros grandes. Observese que esta opción es innecesaria y no se recomienda para sistemas de ficheros que soporten ficheros grandes. Se puede obtener mayor velocidad de cuellos de botella de entrada/salida usando directorios RAID en discos físicos diferentes. Por ahora, el único valor permitido para RAID_TYPE es STRIPED. 1 y RAID0 son alias de STREPED. Si se especifica al opción RAID_TYPE para una tabla MyISAM, también es posible especificar las opciones RAID_CHUNKS y RAID_CHUNKSIZE. El valor máximo para RAID_CHUNCKS es 255. MyISAM creará RAID_CHUNKS subdirectorios con los nombres '00', '01', '02',... '09', '0a', '0b,... en el directorio de la base de datos. En cada uno de esos directorios, MyISAM creará un "table_name.MYD". Cuando se escriban datos al fichero de datos, el manipulador RAID mapea los primeros RAID_CHUNKSIZE *1024 bytes al primer fichero, los siguientes RAID_CHUNKSIZE *1024 bytes al siguiente, y así sucesivamente. RAID_TYPE funciona en cualquier sistema operativo, siempre que se construya MySQL con la opción de configuración --with-raid. Para determinar si el servidor soporta tablas RAID, usar SHOW VARIABLES LIKE 'have_raid' para ver si el valor de la variable es YES.
UNION UNION se usa cuando se quiere usar una colección de tablas idénticas como una. Esto sólo funciona con tablas MERGE. Por el momento es necesario tener los privilegios SELECT, UPDATE y DELETE en las tablas a mapear en una tabla MERGE. Originalmente, todas las tablas mapeadas deben pertenecer a la misma base de datos que la propia tabla MERGE. Esta restricción ha sido eliminada a partir de MySQL 4.1.1.
INSERT_METHOD Si se quiere insertar tados en una tabla MERGE, se debe especificar con INSERT_METHOD dentro de qué la tabla se insertará la fila. INSERT_METHOD es una opción frecuente sólo en tablas MERGE. Esta opción se introdujo en MySQL 4.0.0.
DATA DIRECTORY
INDEX DIRECTORY
Usando DATA DIRECTORY='directory' o INDEX DIRECTORY='directory' se puede especificar dónde colocará el motor de almacenamiento el fichero de datos y el de índices. Este directorio debe ser un camino completo al directorio (no un camino relativo). Esto sólo funciona con tablas MyISAM desde MySQL 4.0, cuando no se está usando la opción --skip-symlink.

A partir de MySQL 3.23, se puede crear una tabla a partir de otra añadiendo la sentencia SELECT al final de la sentencia CREATE TABLE:

CREATE TABLE new_tbl SELECT * FROM orig_tbl;

MySQL creará nuevos campos para todos los elementos del SELECT. Por ejemplo:

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

Esto creará una tabla MyISAM con tres columnas, a, b y c. Hay que tener en cuenta que esas tres columnas de la sentencia SELECT se añaden al lado derecho de la tabla, no superpuestos. Ver el siguiente ejemplo:

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: 0
 
mysql> SELECT * FROM bar;
+------+---+
| m    | n |
+------+---+
| NULL | 1 |
+------+---+
1 row in set (0.00 sec)

Para cada fila en la tabla foo, se inserta una fila en bar con los valores de foo y los valores por defecto para las nuevas columnas.

Si se produce cualquier error mientras se copian los datos a la tabla, esta se eliminará automáticamente y no se creará.

CREATE TABLE ... SELECT no creará indices de forma automática. Esto se ha hecho de forma intencionada para hacer el comando tan flexible como sea posible. Si se quiere tener índices en la tabla creada, se puede especificar después de la sentencias SELECT:

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

Se pueden producir algunas conversiones de tipos de columna. Por ejemplo, el atributo AUTO_INCREMENT no se preserva, y columasn VARCHAR se pueden convertir en CHAR.

Cuando se crea una tabla con CREATE ... SELECT, hay que asegurarse de crear alias para cualquier llamada a función o expresión en la consulta. Si no se hace, la sentencia CREATE podrá fallar o pueden resultar nombres de columna no deseados.

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;

Desde MySQL 4.1, se puede especificar explícitamente el tipo para una columna generada:

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

En MySQL 4.1, también se puede usar LIKE para crear una tabla vacía basada en la definición de otra tabla, incluyendo cualquier atributo de columna e indices que tenga la tabla original:

CREATE TABLE new_tbl LIKE orig_tbl;

CREATE TABLE ... LIKE no copia ninguna opción de tabla DATA DIRECTORY o INDEX DIRECTORY que se haya especificado en la tabla original, o cualquier definición de clave foránea.

Se puede preceder el SELECT por IGNORE o REPLACE para indicar como manipular registros que dupliquen claves únicas. Con IGNORE, los nuevos registros que dupliquen la clave única de un registro existente serán descartados. Con REPLACE, los nuevos registros reemplazan a los que tengan el mismo valor de clave única. Si no se especifica IGNORE ni REPLACE, la repetición de claves únicas producirá un error.

Para asegurar que el diario de modificación puede ser usado para recrear las tablas originales, MySQL no permite la inserción concurrente durante CREATE TABLE ... SELECT.

Cambios de especificaciones de columna sin notificación  

En algunos casos, MySQL hace cambios en las especificaciones de columna dadas en una sentencia CREATE TABLE o ALTER TABLE sin notificarlo:

Para comprobar si MySQL ha usado un tipo de columna diferente del especificado, se puede usar una sentencia DESCRIBE o SHOW CREATE TABLE después de crear la tabla o alterar una tabla.

Pueden producirse otros cambios de tipo de columna si se comprime una tabla usando myisampack.

(4.1.1)