Por lo que pude descubrir, muchos DBMS (por ejemplo, mysql, postgres, mssql) usan combinaciones fk y pk solo para restringir los cambios en los datos, pero rara vez se usan de forma nativa para seleccionar automáticamente columnas para unir (como la combinación natural hace con nombres). ¿Porqué es eso? Si ya ha definido una relación entre 2 tablas con un pk / fk, ¿por qué la base de datos no puede darse cuenta de que si me uno a esas tablas quiero unirlas en las columnas pk / fk?
EDITAR: para aclarar esto un poco:
supongamos que tengo una tabla1 y una tabla2. la tabla 1 tiene una clave externa en la columna a, que hace referencia a la clave primaria en la tabla 2, la columna b. Ahora, si me uno a estas tablas, tendré que hacer algo como esto:
SELECT * FROM table1
JOIN table2 ON table1.a = table2.b
Sin embargo, ya definí usando mis claves que table1.a hace referencia a table2.b, por lo que me parece que no debería ser difícil hacer que un sistema DBMS use automáticamente table1.a y table2.b como columnas de unión, tal que uno simplemente puede usar:
SELECT * FROM table1
AUTO JOIN table2
Sin embargo, muchos DBMS no parecen implementar algo como esto.
fuente
NATURAL JOIN
(por lo que generalmente las evito), pero no creo que eso en sí mismo deba significar que un dbms no podría implementar una forma automática de unir tablas basadas en claves foráneas.AUTO JOIN mytable THROUGH myrelation
, sería muy bueno.InnerJoin(SRC_TABLE.rDEST_TABLE.REL_NAME_F01)
Una clave foránea está destinada a restringir los datos. es decir, hacer cumplir la integridad referencial. Eso es. Nada más.
Puede tener varias claves externas para la misma tabla. Considere lo siguiente cuando un envío tiene un punto de inicio y un punto final.
Es posible que desee unirse en función del estado de recogida. Quizás quieras unirte al estado de entrega. ¡Quizás quieras realizar 2 uniones para ambos! El motor sql no tiene forma de saber lo que quieres.
A menudo cruzará valores escalares de unión. Aunque los escalares generalmente son el resultado de cálculos intermedios, a veces tendrá una tabla de propósito especial con exactamente 1 registro. Si el motor intentara detectar una clave extranjera para la unión ... no tendría sentido porque las uniones cruzadas nunca coinciden con una columna.
En algunos casos especiales, se unirá en columnas donde ninguna de las dos es única. Por lo tanto, la presencia de un PK / FK en esas columnas es imposible.
Usted puede pensar que los puntos 2 y 3 anteriores no son relevantes ya que sus preguntas acerca de cuándo es allí ES una relación única PK / FK entre las mesas. Sin embargo, la presencia de un solo PK / FK entre las tablas no significa que no pueda tener otros campos para unirse además del PK / FK. El motor sql no sabría en qué campos desea unirse.
Digamos que tiene una tabla "USA_States" y otras 5 tablas con un FK para los estados. Las "cinco" tablas también tienen algunas claves externas entre sí. ¿Debería el motor SQL unir automáticamente las "cinco" tablas con "USA_States"? ¿O debería unir los "cinco" entre sí? ¿Ambos? Puede configurar las relaciones para que el motor sql entre en un bucle infinito tratando de unir cosas. En esta situación, es imposible para el motor SQL adivinar lo que quiere.
En resumen: PK / FK no tiene nada que ver con las uniones de tabla. Son cosas separadas no relacionadas. Es solo un accidente de la naturaleza que a menudo te unes en las columnas PK / FK.
¿Desea que el motor SQL adivine si es una unión completa, izquierda, derecha o interna? No lo creo. Aunque podría decirse que sería un pecado menor que adivinar las columnas para unirse.
fuente
SQL y teoría relacional: cómo escribir código SQL preciso por fecha CJ
El SQL estándar ya tiene dicha característica, conocida como
NATURAL JOIN
, y se ha implementado en mySQL.Aunque su sugerencia no es tan valiosa, parece razonable. Con SQL Server (que carece de soporte
NATURAL JOIN
), uso SQL Prompt en Management Studio: cuando escribo un,INNER JOIN
su InteliSense sugiereON
cláusulas basadas en nombres de atributos comunes y claves foráneas y me parece muy útil. Sin embargo, no tengo muchas ganas de ver un nuevo tipo de combinación SQL (estándar) para esto.fuente
¡SQL vino primero!
Las restricciones de Claves externas y Claves externas llegaron más tarde y son esencialmente una optimización para aplicaciones de estilo de "transacción".
Las bases de datos relacionales se concibieron originalmente como un método para aplicar consultas complejas en conjuntos de datos de manera matemáticamente demostrable utilizando álgebra relacional. IE para un conjunto dado de datos y una consulta dada siempre hay una única respuesta correcta.
Las bases de datos relacionales han recorrido un largo camino desde entonces, y su uso principal como la capa de persistencia para los sistemas transaccionales no fue lo que CODD et. Todo previsto.
Sin embargo, el organismo de estándares ANSI para todos sus objetivos en conflicto y políticas de proveedores siempre se ha esforzado por preservar las propiedades "matemáticamente demostrables" de SQL.
Si permitía que la base de datos dedujera las propiedades de unión a partir de datos de clave externa "ocultos", perdería esta propiedad (tenga en cuenta la ambigüedad si hubiera más de un conjunto de claves externas definidas).
Además, un programador que lea el SQL no necesariamente sabría qué claves externas se definieron actualmente para las dos tablas y necesitaría examinar el esquema de la base de datos para determinar qué estaba haciendo la consulta.
fuente
Si bien ha definido una relación de clave externa que no significa que es así como desea unir las tablas en todas las consultas. Es el método más probable para unir las tablas, pero hay casos en los que no es correcto.
fuente
Puede estar operando con una suposición falsa. Dices "hasta donde puedes averiguar" pero no das ninguna prueba empírica o probatoria. Si pk o fk son el mejor índice para una consulta, se utilizará. No sé por qué estás viendo esto, pero supongo que son consultas mal formadas.
Edite ahora que la pregunta se ha reescrito por completo: el caso que está describiendo sería solo para un conjunto muy pequeño de consultas. ¿Qué pasa si hay 12 mesas unidas? ¿Qué pasa si no hay FKs? ... Incluso si hubiera una unión predeterminada, siempre especificaría la unión solo para facilitar la lectura. (No quiero tener que mirar los datos y luego tratar de averiguar en qué se está uniendo)
Algunas herramientas de consulta realmente hacen una unión automática por usted y luego le permiten eliminar o editar la unión. Creo que el generador de consultas de MS Access hace esto.
Por último, el estándar ANSII establece que la unión debe especificarse. Esa es razón suficiente para no permitirlo.
fuente
Hay muchas razones por las cuales la base de datos no puede hacer esto de manera segura, incluido el hecho de que agregar / eliminar claves externas cambiará el significado de las consultas preescritas, incluidas las consultas en el código fuente de la aplicación. La mayoría de las bases de datos tampoco tienen un buen conjunto de claves foráneas que cubran todas las combinaciones posibles que probablemente desee. También para bien o para mejor, las claves externas a menudo se eliminan para acelerar los sistemas y no se pueden usar en tablas que se cargan en el orden "incorrecto" del archivo.
Sin embargo, no hay ninguna razón por la cual una herramienta de diseño de consultas o el editor de texto no puedan completar automáticamente una combinación con la ayuda de Foreign Keys de la misma manera que le dan inteligencia sobre el nombre de la columna. Puede editar la consulta si la herramienta se equivocó y guardar una consulta completamente definida. Tal herramienta también podría hacer uso útil de la convención de nombrar columnas Foreign Keys por el nombre de la tabla "padre" y las columnas con el mismo nombre en la tabla padre / hijo, etc.
(¡Mi esposa todavía no puede entender la diferencia entre Management Studio y Sql Server y habla sobre iniciar el servidor SQL cuando inicia Management Studio!)
fuente
La unión natural se une "automáticamente" a la igualdad de las columnas comunes, pero solo debe escribir eso si eso es lo que desea en función de los significados de la tabla y el resultado deseado. No hay forma "automática" de saber cómo dos tablas "deberían" unirse o de cualquier otra forma que cualquier tabla "debería" aparecer en una consulta. No necesitamos conocer restricciones para consultar. Su presencia solo significa que las entradas pueden ser limitadas y, en consecuencia, la salida también puede serlo. Podría definir algún tipo de operador join_on_fk_to_pk que se una "automáticamente" a las restricciones declaradas; pero si desea que el significado de la consulta permanezca igual si solo cambian las restricciones pero no los significados de la tabla, entonces tendría que cambiar esa consulta para no usar las nuevas constaciones declaradas.ya deja el significado igual a pesar de cualquier cambio de restricción .
Las restricciones (incluyendo PK, FK, UNIQUE y CHECK) no afectan el significado de las tablas. Por supuesto, si los significados de la tabla cambian, las restricciones podrían cambiar. Pero si las restricciones cambian, no significa que las consultas deberían cambiar.
No es necesario conocer las restricciones para consultar. Conocer las restricciones significa que podemos usar expresiones adicionales que sin la retención de la restricción no devolverían la misma respuesta. Por ejemplo, esperar a través de UNIQUE que una tabla tiene una fila, por lo que podemos usarla como escalar. Estas consultas pueden romperse si se asumió la restricción pero no se declaró. Pero declarar una restricción que la consulta no asumió no puede romperla.
¿Existe alguna regla general para construir una consulta SQL a partir de una descripción legible por humanos?
fuente
La razón es que existe el IDIOMA, y luego están los principios subyacentes. El lenguaje es escaso y carece de muchas características que esperaría ver en un lenguaje de propósito general. Esto simplemente es una buena característica que no se ha agregado al idioma y que probablemente no se agregará. No es un idioma muerto, así que hay algo de esperanza, pero no sería optimista.
Como otros han señalado, algunas implementaciones usan una extensión donde join (column) une dos tablas basadas en un nombre de columna común, que es algo similar. Pero no está muy extendido. Tenga en cuenta que esta extensión es diferente de la
SELECT * FROM employee NATURAL JOIN department;
sintaxis, que no incluye una forma de especificar qué columnas usar. Tampoco se basan en una relación entre las tablas, lo que las hace poco confiables (la sintaxis de unión natural más que la extensión).No hay ningún obstáculo fundamental para la "tabla de unión interna en PKFK", donde PKFK es una palabra clave que significa "la relación de clave externa definida entre las dos tablas", puede haber problemas con múltiples fk en la misma tabla, pero eso podría simplemente causar un error. La pregunta es si las personas que diseñan el idioma consideran que a) es una buena idea yb) es mejor trabajar que algún otro cambio de idioma ...
fuente
Si se supone que omitir la cláusula ON sigue los campos en función de la integridad referencial, ¿cómo haría un producto cartesiano?
Editar: usar AUTO Las ventajas de esto es escribir un poco menos y no es necesario saber cómo se unen ni recordar una combinación complicada. Si la relación cambia, se maneja automáticamente, pero eso rara vez ocurre, excepto en el desarrollo temprano.
Lo que debe hacer ahora es decidir si todas sus uniones AUTO se mantienen durante un cambio de relación para que coincida con la intención de su declaración de selección.
fuente
Partes de la razón son:
1: en teoría, puede unir tablas en columnas arbitrarias de las dos tablas. Si bien esto no es una práctica común, es válido. Recuerde que SQL es como un lenguaje de programación, no comprende qué información hay dentro de las columnas del curso y los nombres, para SQL, no significan mucho en este sentido.
2: existen diferentes tipos de combinaciones (izquierda, derecha, interior): las combinaciones internas son solo 1 de ellas.
3 - El estándar SQL puede guiarse por el principio de ser un lenguaje de nivel inferior que permite que los dialectos de nivel superior formen inteligencia al usarlo. La comparación es algo más clara si piensa en un lenguaje de cuarta generación frente a un lenguaje de tercera generación. De hecho, una herramienta que he usado, IEF, le permitió escribir algo como esto:
En resumen, su sugerencia es interesante y podría implementarse como parte de la norma o como un procedimiento almacenado (por defecto sería una unión interna).
fuente
Tiddo, creo que tienes toda la razón, SQL sobre ese tema es bastante tonto , y recuerdo haber pensado lo mismo que hiciste sobre las claves externas mientras aprendías SQL hace unos diez años.
Ok, dado eso, eventualmente tuve que aprobar ese examen; y para pasarlo, tuve que dejarlo ir . SQL es más un desastre de lo que cualquiera puede admitir, su ruta de estandarización es un completo desastre y algunas implementaciones son amenazantes . Aún así es bastante útil, en general. (No soy un ludita K / V)
Claves foráneas, entonces ... no es tan útil en absoluto. Son un concepto importante en el modelo relacional , está bien, pero la función SQL con el mismo nombre no se compara bien.
Decirle recta: no utilice esta característica SQL llamada
Foreign Key
en absoluto , hasta llegar a algún gran sistema con problemas de rendimiento. Explícitamente decirle al motor de qué campo es una clave externa y que no se está sólo se utiliza para la indexación, y es invisible para el usuario db.¿Es engañoso?
Si.
¿Lo van a hacer más poderoso ahora, después de 30 años de personas engañadas?
De ninguna manera.
Ignorando completamente las claves foráneas hasta que sea necesario ... ¿ solucionó SQL para mí?
¡Si!
¿Y por qué diablos todo esto sucedió en primer lugar?
Bueno, la característica que llamamos claves foráneas se agregó más tarde a SQL; SQL es un estándar que evolucionó con el tiempo, de abajo hacia arriba. Los vendedores implementaron características absurdas, mientras que los cuerpos estándar se pusieron en la cara.
Las claves foráneas, como se dijo, solo estaban destinadas a la indexación y no había una construcción JOIN disponible. (las uniones donde se realizan con
SELECT
consultas, lasJOIN
consultas son bastante recientes y solo están destinadas a laSELECT
funcionalidad de alias ) Probablemente, aunque llamar a ese indicador de indexaciónFOREIGN KEY
, fue un ingenioso truco de nombres sobre conceptos de teoría de base de datos relacional.fuente