Siéntete en la libertad de divulgar nuestros tutoriales y códigos en tus redes, danos de tu ayuda para ampliar esta comunidad.
Solución:
Qué es a LATERAL
¿entrar?
La función se introdujo con PostgreSQL 9.3.
Citando el manual:
Subconsultas que aparecen en
FROM
puede ser precedido por el key palabra
LATERAL
. Esto les permite hacer referencia a las columnas proporcionadas por
FROM
elementos. (Sin queLATERAL
, cada subconsulta se evalúa de forma independiente y, por lo tanto, no puede hacer referencia cruzada a ninguna otraFROM
ít.)Funciones de tabla que aparecen en
FROM
También puede ir precedido de la key
palabraLATERAL
, pero para las funciones el key la palabra es opcional; Los argumentos de la función pueden contener referencias a columnas proporcionadas porFROM
artículos en cualquier caso.
Allí se dan ejemplos de código básico.
Más como un correlacionado subconsulta
A LATERAL
join es más como una subconsulta correlacionada, no una subconsulta simple, en que las expresiones a la derecha de un LATERAL
unirse se evalúan una vez para cada fila que queda de ella, como un correlacionado subconsulta – mientras se evalúa una subconsulta simple (expresión de tabla) una vez solo. (Sin embargo, el planificador de consultas tiene formas de optimizar el rendimiento para ambos).
Respuesta relacionada con ejemplos de código para ambos lado a lado, resolviendo el mismo problema:
- Optimizar la consulta GROUP BY para recuperar la última fila por usuario
Por regresar más de una columna, a LATERAL
Unir es típicamente más simple, más limpio y más rápido.
Además, recuerde que el equivalente de una subconsulta correlacionada es LEFT JOIN LATERAL ... ON true
:
- Llamar a una función de devolución de conjuntos con un array argumento varias veces
Cosas que una subconsulta no puede hacer
Ahí son cosas que un LATERAL
join puede hacerlo, pero una subconsulta (correlacionada) no puede (fácilmente). Una subconsulta correlacionada solo puede devolver un valor único, no varias columnas ni varias filas, con la excepción de las llamadas a funciones simples (que multiplican las filas de resultados si devuelven varias filas). Pero incluso ciertas funciones de devolución de conjuntos solo están permitidas en el FROM
cláusula. Me gusta unnest()
con múltiples parámetros en Postgres 9.4 o posterior. El manual:
Esto solo está permitido en el
FROM
cláusula;
Entonces esto funciona, pero no se puede reemplazar (fácilmente) con una subconsulta:
CREATE TABLE tbl (a1 int[], a2 int[]);
SELECT * FROM tbl, unnest(a1, a2) u(elem1, elem2); -- implicit LATERAL
La coma (,
) en el FROM
la cláusula es una notación corta para CROSS JOIN
.LATERAL
se asume automáticamente para funciones de tabla.
Sobre el caso especial de UNNEST( array_expression [, ... ] )
:
- ¿Cómo se declara que una función de retorno de conjunto solo se permita en la cláusula FROM?
Funciones de retorno de conjuntos en el SELECT
lista
También puede utilizar funciones de devolución de conjuntos como unnest()
en el SELECT
lista directamente. Esto solía exhibir un comportamiento sorprendente con más de una función en el mismo SELECT
lista hasta Postgres 9.6. Pero finalmente se ha saneado con Postgres 10 y es una alternativa válida ahora (incluso si no es SQL estándar). Ver:
- ¿Cuál es el comportamiento esperado para múltiples funciones de retorno de conjuntos en la cláusula SELECT?
Sobre la base del ejemplo anterior:
SELECT *, unnest(a1) AS elem1, unnest(a2) AS elem2
FROM tbl;
Comparación:
dbfiddle para pg 9.6 aquí
dbfiddle para la página 10 aquí
Aclarar la desinformación
El manual:
Para el
INNER
yOUTER
tipos de combinación, se debe especificar una condición de combinación, es decir, exactamente una deNATURAL
,ON
join_condition, oUSING
(join_column [, …]). Vea a continuación el significado.
ParaCROSS JOIN
, ninguna de estas cláusulas puede aparecer.
Entonces estas dos consultas son válidas (incluso si no son particularmente útiles):
SELECT *
FROM tbl t
LEFT JOIN LATERAL (SELECT * FROM b WHERE b.t_id = t.t_id) t ON TRUE;
SELECT *
FROM tbl t, LATERAL (SELECT * FROM b WHERE b.t_id = t.t_id) t;
Si bien este no es:
SELECT *
FROM tbl t
LEFT JOIN LATERAL (SELECT * FROM b WHERE b.t_id = t.t_id) t;
Es por eso que el ejemplo de código de Andomar es correcto (el CROSS JOIN
no requiere una condición de unión) y Attila’s es no estaba.
La diferencia entre unlateral
y un lateral
Unir radica en si puede mirar a la fila de la tabla de la izquierda. Por ejemplo:
select *
from table1 t1
cross join lateral
(
select *
from t2
where t1.col1 = t2.col1 -- Only allowed because of lateral
) sub
Esta “mirada hacia el exterior” significa que la subconsulta debe evaluarse más de una vez. Después de todo, t1.col1
puede asumir muchos valores.
Por el contrario, la subconsulta después de una no-lateral
unirse se puede evaluar una vez:
select *
from table1 t1
cross join
(
select *
from t2
where t2.col1 = 42 -- No reference to outer query
) sub
Como se requiere sin lateral
, la consulta interna no depende de ninguna manera de la consulta externa. A lateral
consulta es un ejemplo de una correlated
consulta, debido a su relación con filas fuera de la consulta en sí.
Primero, la aplicación lateral y transversal es lo mismo. Por lo tanto, también puede leer sobre Cross Apply. Dado que se implementó en SQL Server durante mucho tiempo, encontrará más información al respecto que Lateral.
Segundo, de acuerdo a mi entendimiento, no hay nada que no pueda hacer usando subconsulta en lugar de usar lateral. Pero:
Considere la siguiente consulta.
Select A.*
, (Select B.Column1 from B where B.Fk1 = A.PK and Limit 1)
, (Select B.Column2 from B where B.Fk1 = A.PK and Limit 1)
FROM A
Puede utilizar lateral en esta condición.
Select A.*
, x.Column1
, x.Column2
FROM A LEFT JOIN LATERAL (
Select B.Column1,B.Column2,B.Fk1 from B Limit 1
) x ON X.Fk1 = A.PK
En esta consulta no puede utilizar la combinación normal, debido a la cláusula de límite. La aplicación lateral o cruzada se puede utilizar cuando no existe una condición de unión simple.
Hay más usos para la aplicación lateral o transversal, pero este es el más común que encontré.
Tienes la opción de añadir valor a nuestra información tributando tu experiencia en las interpretaciones.