Академический Документы
Профессиональный Документы
Культура Документы
SQL
Orígenes y evolución
Los orígenes del SQL están ligados a los de las bases de datos relacionales. En 1970 E.
F. Codd propone el modelo relacional y asociado a este un sublenguaje de acceso a los
datos basado en el cálculo de predicados. Basándose en estas ideas, los laboratorios de
IBM definen el lenguaje SEQUEL (Structured English QUEry Language) que más
tarde sería ampliamente implementado por el SGBD experimental System R,
desarrollado en 1977 también por IBM. Sin embargo, fue Oracle quien lo introdujo por
primera vez en 1979 en un programa comercial.
Sin embargo este primer estándar no cubre todas las necesidades de los desarrolladores
e incluye funcionalidades de definición de almacenamiento que se consideraron
suprimir. Así que en 1992 se lanza un nuevo estándar ampliado y revisado del SQL
llamado SQL-92 o SQL2.
Si no conoces todavía las tablas que utilizaremos para los ejemplos y ejercicios
clic aquí
SQL > SQL Sintaxis
En esta página, enumeramos la sintaxis SQL para cada uno de los comandos SQL en esta guía de
referencia. Para obtener explicaciones detalladas para cada sintaxis SQL, por favor diríjase a la
sección individual haciendo clic en la palabra clave.
El propósito de esta página es brindar una página de referencia rápida para la sintaxis SQL. Le
sugerimos que agregue esta página a favoritos ahora presionando Control-D para que pueda
tener esta página de sintaxis a mano.
Select
SELECT "nom de colonne" FROM "nombre_tabla"
Distinct
SELECT DISTINCT "nombre_columna"
FROM "nombre_tabla"
Where
SELECT "nombre_columna"
FROM "nombre_tabla"
WHERE "condition"
And/Or
SELECT "nombre_columna"
FROM "nombre_tabla"
WHERE "condición simple"
{[AND|OR] "condición simple"}+
In
SELECT "nombre_columna"
FROM "nombre_tabla"
WHERE "nombre_columna" IN ('valor1', 'valor2', ...)
Between
SELECT "nombre_columna"
FROM "nombre_tabla"
WHERE "nombre_columna" BETWEEN 'valor1' AND 'valor2'
Like
SELECT "nombre_columna"
FROM "nombre_tabla"
WHERE "nombre_columna" LIKE {patrón}
Order By
SELECT "nombre_columna"
FROM "nombre_tabla"
[WHERE "condición"]
ORDER BY "nombre_columna" [ASC, DESC]
Count
SELECT COUNT("nombre_columna")
FROM "nombre_tabla"
Group By
SELECT "nombre_columna 1", SUM("nombre_columna 2")
FROM "nombre_tabla"
GROUP BY "nombre_columna 1"
Having
SELECT "nombre_columna 1", SUM("nombre_columna 2")
FROM "nombre_tabla"
GROUP BY "nombre_columna 1"
HAVING (condición de función aritmética)
Create Table
CREATE TABLE "nombre_tabla"
("columna 1" "tipo_de_datos_para_columna_1",
"columna 2" "tipo_de_datos_para_columna_2",
... )
Drop Table
DROP TABLE "nombre_tabla"
Truncate Table
TRUNCATE TABLE "nombre_tabla"
Insert Into
INSERT INTO "nombre_tabla" ("colonne 1", "colonne 2", ...)
valorS ("valor 1", "valor 2", ...)
Update
UPDATE "nombre_tabla"
SET "colonne 1" = [nuevo valor]
WHERE {condition}
Delete From
DELETE FROM "nombre_tabla"
WHERE {condición}
Sintaxis de la sentencia SELECT (consultas
simples)
Características generales
El SQL es un lenguaje de acceso a bases de datos que explota la flexibilidad y potencia
de los sistemas relacionales permitiendo gran variedad de operaciones sobre los
mismos.
Optimización
Como ya se dijo arriba, y como suele ser común en los lenguajes de acceso a bases de
datos de alto nivel, el SQL es un lenguaje declarativo. O sea, que especifica qué es lo
que se quiere y no cómo conseguirlo, por lo que una sentencia no establece
explícitamente un orden de ejecución.
Existe una ampliación de SQL conocida como FSQL (Fuzzy SQL, SQL difuso) que
permite el acceso a bases de datos difusas, usando la lógica difusa. Este lenguaje ha sido
implementado a nivel experimental y está evolucionando rápidamente.
Este manual está basado en el SQL del motor de base de datos que utiliza el Access2000,
el Microsoft Jet 4.x, para que los ejemplos y ejercicios se puedan ejecutar y probar.
Para crear y después ejecutar una sentencia SQL en Access, lo fácil es utilizar la ventana
SQL de las consultas.
Al apretar el botón cerrar de la pantalla anterior se abre esta ventana donde introducimos
la sentencia SQL.
Una vez escrita sólo nos queda ver si está bien hecha.
Hacer clic sobre el botón de la barra de herramientas para ejecutar la sentencia.
Si nos hemos equivocado a la hora de escribir la sintaxis, Access nos saca un mensaje de
error y muchas veces el cursor se queda posicionado en la palabra donde ha saltado el
error. Ojo, a veces el error está antes o después de donde se ha quedado el cursor.
Las jerarquías son muy comunes en los sistemas de información, se utilizan para organizar
elementos por orden de importancia o por tamaño, como por ejemplo en un sistema de archivos o
en el organigrama de la empresa.
Por lo general cualquier conjunto de elementos en el cual todos los elementos exceptuando al
elemento raíz tienen un solo padre y cero o más hijos, puede ser considerado una jerarquías, o
como también se les conoce, un árbol invertido.
Las desventajas aparecen cuando se trata de recuperar la información de la jerarquía, puesto que
no es posible realizar una sola consulta a la base de datos que devuelva toda o parte de la
jerarquía.
Un ejemplo de una consulta que no resulta fácil de contestar cuando se utilizan las listas de
adyacencia es “Cual es el sueldo total del área de Patricia”.
La primera ayuda para resolver este tipo de consultas vino de la mano de SQL Server 2000 con la
introducción de las Inline Table-Value User-Defined Function. Estas funciones permiten que una
función retorne datos en forma de tabla y tomar el resultado de dicha función como cualquier otra
tabla de la base de datos.
OPEN EmpleadosDirectos
WHILE (@@FETCH_STATUS = 0)
BEGIN
INSERT INTO @retEmpleados
SELECT * FROM dbo.GetIdEmpleados(@EmpleadosDirectos_Id)
FETCH NEXT FROM EmpleadosDirectos
INTO @EmpleadosDirectos_Id
END
CLOSE EmpleadosDirectos
DEALLOCATE EmpleadosDirectos
RETURN
END
Esta función es capaz de devolver todos los identificadores de los empleados que reportan directa
o indirectamente a una persona. Utilizando el resultado de esta función es posible responder a la
consulta “Cual es el sueldo total del área de Patricia”, primero buscando el Id de Patricia, luego
llamando a la función GetIdEmpleados con ese Id como parámetro, realizando un join entre el
resultado de la función la tabla empleado, para finalmente obtener la suma de los sueldos de los
empleados.
En SQL Server 2005 se introdujo una nueva funcionalidad al motor que facilita aun más el trabajo
con jerarquías. Esta nueva funcionalidad se llama Recursive Common Table Expressions (Recursive
CTE) y permite realizar una consulta recursiva sin tener que definir una función para realizar dicha
operación.
Esta consulta se resuelve de forma mucho más eficiente pues el motor entiende de mejor manera
que es lo que se quiere hacer, con lo que se obtienen mejoras considerable. Algunas pruebas
realizadas en SQL 2005 utilizando las 2 técnicas descritas mostraron que las consultas que
utilizaban los Recursive CTEs demoraban 4 a 10 veces menos que las que utilizaban las técnicas
descritas para la versión para 2000.
La versión de SQL Server 2008 trae aun más mejoras al desempeño y a la facilidad de uso de las
consultas sobre jerarquías. En un próximo post escribiré sobre el nuevo tipo de datos llamado
HierarchyID
Las vinculaciones entre tablas se realizan mediante la cláusula INNER que combina
registros de dos tablas siempre que haya concordancia de valores en un campo
común. Su sintaxis es:
En donde:
tb1, tb2 Son los nombres de las tablas desde las que se combinan los registros.
Son los nombres de los campos que se combinan. Si no son numéricos,
campo1,
los campos deben ser del mismo tipo de datos y contener el mismo tipo
campo2
de datos, pero no tienen que tener el mismo nombre.
Es cualquier operador de comparación relacional: =, <,<>, <=, =>, ó
comp
>.
Se puede utilizar una operación INNER JOIN en cualquier cláusula FROM. Esto crea
una combinación por equivalencia, conocida también como unión interna. Las
combinaciones equivalentes son las más comunes; éstas combinan los registros de
dos tablas siempre que haya concordancia de valores en un campo común a ambas
tablas. Se puede utilizar INNER JOIN con las tablas Departamentos y Empleados
para seleccionar todos los empleados de cada departamento. Por el contrario, para
seleccionar todos los departamentos (incluso si alguno de ellos no tiene ningún
empleado asignado) se emplea LEFT JOIN o todos los empleados (incluso si alguno
no está asignado a ningún departamento), en este caso RIGHT JOIN.
SELECT
NombreCategoria, NombreProducto
FROM
Categorias
INNER JOIN
Productos
ON
Categorias.IDCategoria = Productos.IDCategoria
SELECT campos FROM tb1 INNER JOIN (tb2 INNER JOIN [( ]tb3
[INNER JOIN [( ]tablax [INNER JOIN ...)]
ON tb3.campo3 comp tbx.campox)]
ON tb2.campo2 comp tb3.campo3)
ON tb1.campo1 comp tb2.campo2
Un LEFT JOIN o un RIGHT JOIN puede anidarse dentro de un INNER JOIN, pero un
INNER JOIN no puede anidarse dentro de un LEFT JOIN o un RIGHT JOIN.
Ejemplo:
SELECT DISTINCT
Sum(PrecioUnitario * Cantidad) AS Sales,
(Nombre + ' ' + Apellido) AS Name
FROM
Empleados
INNER JOIN(
Pedidos
INNER JOIN
DetallesPedidos
ON
Pedidos.IdPedido = DetallesPedidos.IdPedido)
ON
Empleados.IdEmpleado = Pedidos.IdEmpleado
GROUP BY
Nombre + ' ' + Apellido
(Crea dos combinaciones equivalentes: una entre las tablas Detalles de pedidos y
Pedidos, y la otra entre las tablas Pedidos y Empleados. Esto es necesario ya que la
tabla Empleados no contiene datos de ventas y la tabla Detalles de pedidos no
contiene datos de los empleados. La consulta produce una lista de empleados y sus
ventas totales.)
No obstante, los INNER JOIN ORACLE no es capaz de interpretarlos, pero existe una
sintaxis en formato ANSI para los INNER JOIN que funcionan en todos los sistemas.
Tomando como referencia la siguiente sentencia:
SELECT
Facturas.*,
Albaranes.*
FROM
Facturas
INNER JOIN
Albaranes
ON
Facturas.IdAlbaran = Albaranes.IdAlbaran
WHERE
Facturas.IdCliente = 325
La transformación de esta sentencia a formato ANSI sería la siguiente:
SELECT
Facturas.*,
Albaranes.*
FROM
Facturas, Albaranes
WHERE
Facturas.IdAlbaran = Albaranes.IdAlbaran
AND
Facturas.IdCliente = 325
Como se puede observar los cambios realizados han sido los siguientes:
SELECT
Facturas.*,
Albaranes.*
FROM
Facturas, Albaranes
WHERE
Facturas.IdAlbaran = Albaranes.IdAlbaran (+)
AND
Facturas.IdCliente = 325
SELECT
Facturas.*,
Albaranes.*
FROM
Facturas, Albaranes
WHERE
Facturas.IdAlbaran (+) = Albaranes.IdAlbaran
AND
Facturas.IdCliente = 325
Consultas de Autocombinación
SELECT
alias1.columna, alias2.columna, ...
FROM
tabla1 as alias1, tabla2 as alias2
WHERE
alias1.columna = alias2.columna
AND
otras condiciones
Por ejemplo, para visualizar el número, nombre y puesto de cada empleado, junto
con el número, nombre y puesto del supervisor de cada uno de ellos se utilizaría la
siguiente sentencia:
SELECT
t.num_emp, t.nombre, t.puesto, t.num_sup,s.nombre, s.puesto
FROM
empleados AS t, empleados AS s
WHERE
t.num_sup = s.num_emp
Por ejemplo, para listar el grado salarial, nombre, salario y puesto de cada
empleado ordenando el resultado por grado y salario habría que ejecutar la
siguiente sentencia:
SELECT
grados.grado,empleados.nombre, empleados.salario, empleados.puesto
FROM
empleados, grados
WHERE
empleados.salario BETWEEN grados.salarioinferior And grados.salariosuperior
ORDER BY
grados.grado, empleados.salario
Para listar el salario medio dentro de cada grado salarial habría que lanzar esta otra
sentencia:
SELECT
grados.grado, AVG(empleados.salario)
FROM
empleados, grados
WHERE
empleados.salario BETWEEN grados.salarioinferior And grados.salariosuperior
GROUP BY
grados.grado