我在这里好奇。如果我有两张桌子,请说“客户和订单”。 客户端具有唯一的主键ID_Client。订单还具有ID_Client字段以及通过ID_Client字段维护客户表的完整性的关系。
因此,当我想加入两个表时,我会这样做:
SELECT
Orders.*, Clients.Name
FROM
Orders
INNER JOIN
Clients ON Clients.ID_Client = Orders.ID_Client
因此,如果我接受了创建主键的工作,以及表之间的关系,
我是否需要在on子句中明确包含已连接的列?
为什么我不能这样做:
SELECT
Orders.*, Clients.Name
FROM
Orders
INNER JOIN
Clients
因此,SQL应该知道哪些列与两个表相关...
答案 0 :(得分:5)
我曾经遇到过同样的问题,我在Database Administrator Stack Exchange找到了一个很好的解释,下面的答案是我发现的最好的答案,但你也可以参考链接以获得更多解释
外键意味着约束数据。即执行 参照完整性。而已。没别了。
您可以在同一个表中使用多个外键。请考虑以下情况:货件有起点和终点。
table: USA_States StateID StateName table: Shipment ShipmentID PickupStateID Foreign key DeliveryStateID Foreign key
您可能希望根据取件状态加入。也许你想加入交付状态。也许你想要执行2个连接 都! sql引擎无法知道你想要什么。
您经常会交叉加入标量值。虽然标量通常是中间计算的结果,但有时你会有一个 专用表,正好有1条记录。如果引擎试图 检测连接的foriegn键....它没有意义,因为 交叉连接永远不会与列匹配。
在某些特殊情况下,您将加入既不是唯一的列。因此,在这些柱上存在PK / FK 不可能的。
您可能认为上面的第2点和第3点不相关,因为您的问题是关于何时 IS 单个PK / FK关系 表之间。但是存在单个PK / FK之间 表并不意味着你不能有其他字段加入 除了PK / FK。 sql引擎不知道你是哪个字段 想加入。
- 醇>
假设你有一张表“USA_States”,还有另外5张表格带有FK的表格。 “五”表也有几个外键 彼此。应该是sql引擎自动加入“五”表 与“USA_States”?或者它应该加入“五”?都? 您可以设置关系,以便sql引擎进入 无限循环试图将东西连在一起。在这种情况下 不可能让sql引擎猜出你想要的东西。
总结: PK / FK与表连接无关。它们是不相关的东西。这只是你自然的意外事故 经常加入PK / FK专栏。
你想要sql引擎猜测它是完整的,左,右还是 内部联接?我不这么认为。虽然这可能是一个较小的 犯罪而不是猜测要加入的列。
答案 1 :(得分:1)
如果您未在查询中明确指定字段名称,则SQL不知道要使用哪些字段。您不会总是拥有相同名称的字段,并且您不会总是加入主键。例如,关系可以在名为" Client_Address"的两个外键字段之间。和" Delivery_Address"。在这种情况下,您可以轻松地看到如何提供字段名称。
举个例子:
SELECT o.*, c.Name
FROM Clients c
INNER JOIN Orders o
ON o.Delivery_Address = c.Client_Address
答案 2 :(得分:1)
为什么我需要在on子句中明确包含然后加入字段?
是的,因为你仍然需要告诉数据库服务器你想要什么。 "做我的意思"到目前为止,它不属于任何软件系统的功能。
外键是用于强制执行数据完整性的工具。它们没有规定如何连接表格。您可以在任何可通过SQL表达式表达的条件下加入。
换句话说,join子句通过可自由定义的条件将两个表相互关联,在条件的左手侧和右手侧给出两行时,需要将其评估为true。它不一定是外键,它可以是任何条件。
想找到姓氏与您销售的产品相同的人吗?
SELECT
Products.Name,
Clients.LastName
FROM
Products
INNER JOIN Clients ON Products.Name = Clients.LastName
产品和客户之间甚至没有外键,但整个过程仍然有效。
答案 3 :(得分:0)
就是这样。 :)
sql标准说你必须说明要加入哪些列。约束仅适用于参照完整性。使用mysql,join支持“使用(column1,column2)连接表”,但这些列必须存在于两个表中
答案 4 :(得分:0)
此行为不是默认的原因
因为一个表可以有多个列引用回另一个表中的一个列。
在许多遗留数据库中,没有外键约束,但是列是“假定为”引用某些其他表中的某些列。
连接条件并不总是像A.Column = B.Column一样简单。并且名单继续.......
微软的开发人员足够聪明,让我们做出这个决定,而不是他们猜测它将永远是A.Column = B.Column