使用sql联接';s";关于;带“的声明;及;而不是",;其中;
所以我想知道哪一个是最好的性能方面的,如果在这里使用and是很糟糕的做法 比较以下两个查询: 在末尾使用“WHERE”:使用sql联接';s";关于;带“的声明;及;而不是",;其中;,sql,oracle,join,Sql,Oracle,Join,所以我想知道哪一个是最好的性能方面的,如果在这里使用and是很糟糕的做法 比较以下两个查询: 在末尾使用“WHERE”: select c.cust_last_name, o.order_total, oi.quantity from customers c join orders o on (c.customer_id = o.customer_id) join order_items oi on (o.order_id = oi.
select c.cust_last_name,
o.order_total,
oi.quantity
from customers c
join orders o on (c.customer_id = o.customer_id)
join order_items oi on (o.order_id = oi.order_id)
where c.GENDER='M';
select c.cust_last_name,
o.order_total,
oi.quantity
from customers c
join orders o on (c.customer_id = o.customer_id)
join order_items oi on (o.order_id = oi.order_id and c.GENDER='M');
在末尾使用“AND”:
select c.cust_last_name,
o.order_total,
oi.quantity
from customers c
join orders o on (c.customer_id = o.customer_id)
join order_items oi on (o.order_id = oi.order_id)
where c.GENDER='M';
select c.cust_last_name,
o.order_total,
oi.quantity
from customers c
join orders o on (c.customer_id = o.customer_id)
join order_items oi on (o.order_id = oi.order_id and c.GENDER='M');
and根据最后一个on的条件检索与第一个查询完全相同的数据集。这样行吗?在这种情况下,我怀疑使用哪个版本的查询对Oracle会有很大影响。您可以通过查看每个查询的解释计划进行检查
但是,将
c.gender='M'
谓词移到这里的连接条件中是“安全的”,因为您正在进行内部连接。如果您正在执行外部联接,您将看到不同的结果,这取决于该谓词是否位于where或join子句中。在本例中,我怀疑您使用的查询版本对Oracle会有很大影响。您可以通过查看每个查询的解释计划进行检查
但是,将
c.gender='M'
谓词移到这里的连接条件中是“安全的”,因为您正在进行内部连接。如果您正在进行外部联接,您将看到不同的结果,这取决于谓词是在where子句还是join子句中。将条件放在where子句还是on子句中没有区别
但是,是的,您展示的是糟糕的实践,因为和c.GENDER='M'
与表order\u items
中加入哪些记录无关。ON子句中的条件应始终属于其表
订单项目表中具有附加条件的示例如下
join order_items oi on (o.order_id = oi.order_id and and oi.price > 50)
如果你想在ON子句或WHERE子句中看到这一点,这或多或少是个人偏好的问题。您可能会争辩说,您在订单ID上联接表,然后只保留价格高于50的结果,因此联接仅在ID上。或者你可以争辩说你加入了价格>50的订单项目。这两个语句在语义上都是正确的
然而,在on子句中始终将所有标准放在一个表中是一个好习惯。当你改变
inner join order_items oi on (o.order_id = oi.order_id)
where oi.price > 50
到
这实际上仍然是一个内部联接,因为外部联接的记录的价格为NULL,这不符合WHERE子句标准,因此在创建记录之后立即将其删除:-),因此由于其他联接类型,您必须将条件移动到ON子句。把它放在那里不是更好吗 将条件放在WHERE子句还是ON子句中没有区别 但是,是的,您展示的是糟糕的实践,因为
和c.GENDER='M'
与表order\u items
中加入哪些记录无关。ON子句中的条件应始终属于其表
订单项目表中具有附加条件的示例如下
join order_items oi on (o.order_id = oi.order_id and and oi.price > 50)
如果你想在ON子句或WHERE子句中看到这一点,这或多或少是个人偏好的问题。您可能会争辩说,您在订单ID上联接表,然后只保留价格高于50的结果,因此联接仅在ID上。或者你可以争辩说你加入了价格>50的订单项目。这两个语句在语义上都是正确的
然而,在on子句中始终将所有标准放在一个表中是一个好习惯。当你改变
inner join order_items oi on (o.order_id = oi.order_id)
where oi.price > 50
到
这实际上仍然是一个内部联接,因为外部联接的记录的价格为NULL,这不符合WHERE子句标准,因此在创建记录之后立即将其删除:-),因此由于其他联接类型,您必须将条件移动到ON子句。把它放在那里不是更好吗 我认为性能上存在差异,除非您的表中有大量记录,否则差异不会太大 第一种情况是首先根据内部连接获取所有相关记录,然后根据男性进行过滤。您正在加载其中不相关的部分(女性)的所有记录,然后进行筛选 在第二种情况下,根本不会收集不相关的记录,过滤是作为连接操作的一部分完成的
我同意@Radu Gheorghiu,您可能希望将c.GENDER='M'条件提高一个级别。我认为性能上的差异并不显著,除非您的表中有大量记录 第一种情况是首先根据内部连接获取所有相关记录,然后根据男性进行过滤。您正在加载其中不相关的部分(女性)的所有记录,然后进行筛选 在第二种情况下,根本不会收集不相关的记录,过滤是作为连接操作的一部分完成的
我同意@Radu Gheorghiu,你可能想把c.GENDER='M'条件提高一级。我会把
c.GENDER='M'
条件提高一级,在第一个JOIN
上,因为从逻辑上讲,这是它的一部分。如果使用外部连接,语义会有所不同。从性能的角度来看,没有区别。Oracle能够将一个查询转换为另一个查询。两者都有相同的执行计划。你说的对,执行计划保持不变。我刚刚检查了它,oracle对它的解释完全相同。我将把c.GENDER='M'
条件提高一级,在第一个连接上,因为这是它的一部分,从逻辑上讲,如果使用外部连接,则会产生语义差异。从性能的角度来看,没有区别。Oracle能够将一个查询转换为另一个查询。两者都有相同的执行计划。你说的执行计划保持不变是对的。我刚刚检查了它,oracle对它的解释与我的理解完全相同