inner - ¿Puedes definir tablas "literales" en SQL?
mysql inner join subquery (7)
CREAR TABLA TEMPORAL (ID int, Nombre char (100)) SELECCIONAR ....
Lea más en: http://dev.mysql.com/doc/refman/5.0/en/create-table.html
(cerca de la parte inferior)
Esto tiene la ventaja de que si hay algún problema al rellenar la tabla (desajuste del tipo de datos), la tabla se descarta automáticamente.
Una respuesta temprana usó una cláusula FROM SELECT. Si es posible, úselo porque ahorra el dolor de cabeza de limpiar la mesa.
La desventaja (que puede no importar) con FROM SELECT es qué tan grande es el conjunto de datos creado. Una tabla temporal permite la indexación que puede ser crítica. Para la consulta posterior. Parece contra-intuitivo, pero incluso con un conjunto de datos de tamaño mediano (~ 1000 filas), puede ser más rápido tener un índice creado para que la consulta funcione.
¿Hay alguna sintaxis de subconsulta SQL que le permita definir, literalmente, una tabla temporal?
Por ejemplo, algo así como
SELECT
MAX(count) AS max,
COUNT(*) AS count
FROM
(
(1 AS id, 7 AS count),
(2, 6),
(3, 13),
(4, 12),
(5, 9)
) AS mytable
INNER JOIN someothertable ON someothertable.id=mytable.id
Esto ahorraría tener que hacer dos o tres consultas: crear una tabla temporal, poner datos en ella y luego usarla en una combinación.
Estoy usando MySQL, pero estaría interesado en otras bases de datos que podrían hacer algo como eso.
En Microsoft T-SQL 2008, el formato es:
SELECT a, b FROM (VALUES (1, 2), (3, 4), (5, 6), (7, 8), (9, 10) ) AS MyTable(a, b)
Es decir, como Jonathan mencionó anteriormente, pero sin la palabra clave ''mesa''.
Ver:
- FROM (T-SQL MSDN docs) (en derivada-tabla), y
- Table Value Constructor (documentos de T-SQL MSDN)
En SQL estándar (SQL 2003 - vea http://savage.net.au/SQL/ ) puede usar:
INSERT INTO SomeTable(Id, Count) VALUES (1, 7), (2, 6), (3, 13), ...
Con un poco más de persecución, también puedes usar:
SELECT * FROM TABLE(VALUES (1,7), (2, 6), (3, 13), ...) AS SomeTable(Id, Count)
Ya sea que estos trabajen en MySQL es un tema aparte, pero siempre puede pedir que se agregue o agregarlo usted mismo (esa es la belleza de Open Source).
En una palabra, sí. Aún mejor IMO si su producto SQL admite expresiones de tabla comunes (CTE), es decir, más sencillo que usar una subconsulta más el mismo CTE puede usarse varias veces, por ejemplo para ''crear'' una tabla de secuencia de enteros únicos entre 0 y 999 en SQL Servidor 2005 y superior:
WITH Digits (nbr) AS
(
SELECT 0 AS nbr UNION ALL SELECT 1 UNION ALL SELECT 2
UNION ALL SELECT 3 UNION ALL SELECT 4 UNION ALL SELECT 5
UNION ALL SELECT 6 UNION ALL SELECT 7 UNION ALL SELECT 8
UNION ALL SELECT 9
),
Sequence (seq) AS
(
SELECT Units.nbr + Tens.nbr + Hundreds.nbr
FROM Digits AS Units
CROSS JOIN Digits AS Tens
CROSS JOIN Digits AS Hundreds
)
SELECT S1.seq
FROM Sequence AS S1;
excepto que en realidad harías algo útil con la tabla Secuencia, por ejemplo, analizar los caracteres de una columna VARCHAR en una tabla base.
SIN EMBARGO, si está utilizando esta tabla, que consiste solo de valores literales, múltiples veces o en múltiples consultas, ¿por qué no hacerla una tabla base en primer lugar? Cada base de datos que uso tiene una tabla de Secuencia de enteros (generalmente 100K filas) porque es muy útil en general.
Encontré este enlace Tablas temporales con MySQL
CREATE TEMPORARY TABLE TempTable ( ID int, Name char(100) ) TYPE=HEAP;
INSERT INTO TempTable VALUES( 1, "Foo bar" );
SELECT * FROM TempTable;
DROP TABLE TempTable;
Puedes hacerlo en PostgreSQL:
=> select * from (values (1,7), (2,6), (3,13), (4,12), (5,9) ) x(id, count);
id | count
----+-------
1 | 7
2 | 6
3 | 13
4 | 12
5 | 9
Supongo que podrías hacer una subconsulta con varios SELECT
s combinados con UNION
s.
SELECT a, b, c, d
FROM (
SELECT 1 AS a, 2 AS b, 3 AS c, 4 AS d
UNION ALL
SELECT 5 , 6, 7, 8
) AS temp;