我将三个表名,均放在from⼦句之后,由于表order和表orderitems均含有order_num,造成select和order字句中的歧义,于是我在order_num前加⼊了order.
如下图:
select cust_der_num,sum(quantity*item_price) as ordertotal
from customers,orders,orderitems
where customers.cust_id=orders.cust_id
der_der_num
group by cust_name, der_num
ORDER BY cust_name, order_num;
3.我们重新看⼀下第11课的挑战题2。编写SQL语句,检索订购产品BR01的⽇期,这⼀次使⽤联结和简单的等联结语法。输出应该与第11课的输出相同。
下⾯是11章的第⼆题
(你想知道订购BR01产品的⽇期。编写SQL语句,使⽤⼦查询来确定哪些订单(在OrderItems中)购买了prod_id为BR01的产品,然后从Orders表中返回每个产品对应的顾客ID(cust_id)和订单⽇期(order_date)。按订购⽇期对结果进⾏排序。)
(1)简答的等联结
select cust_id,order_date
from orders,OrderItems
where prod_id ='BR01' der_num=OrderItems .order_num
(2)联结
select cust_id,order_date
from Orders
inner join OrderItems
on prod_id ='BR01' der_num=OrderItems .order_num
4.很有趣,我们再试⼀次。重新创建为第11课挑战题3编写的SQL语句,这次使⽤ANSI的INNERJOIN语法。在之前编写的代码中使⽤了两个嵌套的⼦查询。要重新创建它,需要两个INNER JOIN语句,每个语句的格式类似于本课讲到的INNERJOIN⽰例,⽽且不要忘
记WHERE⼦句可以通过prod_id进⾏过滤。
(3.现在我们让它更具挑战性。在上⼀个挑战题,返回购买prod_id为BR01的产品的所有顾客的电⼦邮件(Customers表中的
cust_email)。提⽰:这涉及SELECT语句,最内层的从OrderItems表返回order_num,中间的从Customers表返回cust_id。)
select cust_email
from customers
inner join orders on Orders.cust_id=customers.cust_id
inner join OrderItems der_num=OrderItems .order_num
where prod_id ='BR01'
5.再让事情变得更加有趣些,我们将混合使⽤联结、聚合函数和分组。准备好了吗?回到第10课,当时的挑战是要求查值等于或⼤于1000的所有订单号。这些结果很有⽤,但更有⽤的是订单数量⾄少达到这个数的顾客名称。因此,编写SQL语句,使⽤联结从Customers表返回顾客名称(cust_name),并从OrderItems表返回所有订单的总价。提⽰:要联结这些表,还需要包括Orders表(因为Customers表与OrderItems表不直接相关,Customers表与Orders表相关,⽽Orders表与OrderItems表相关)。不要忘记GROUP BY和HAVING,并按顾客名称对结果进⾏排序。你可以使⽤简单的等联结或ANSI的INNER JOIN语法。或者,如果你很勇敢,请尝试使⽤两种⽅式编写。
(1)使⽤简单联结
SELECT cust_name, SUM(item_price*quantity) AS total_price
FROM Customers, Orders, OrderItems
WHERE Customers.cust_id = Orders.cust_id
der_num = der_num
每天学点sql经典句子GROUP BY cust_name HAVING SUM(item_price*quantity) >= 1000
ORDER BY cust_name;
⾄于为什么不可以将所有的条件放在having语句中,这⾥给出了答案:
WHERE ⼦句⽤来筛选 FROM ⼦句中指定的操作所产⽣的⾏。
GROUP BY ⼦句⽤来分组 WHERE ⼦句的输出。
HAVING ⼦句⽤来从分组的结果中筛选⾏。
对于可以在分组操作之前或之后应⽤的任何搜索条件,在 WHERE ⼦句中指定它们会更有效。这样可以减少必须分组的⾏数。应当在HAVING ⼦句中指定的搜索条件只是那些必须在执⾏分组操作之后应⽤的搜索条件。
Microsoft SQL Server 2005 之后的查询优化器可以处理这些条件中的⼤多数条件。如果查询优化器确定 HAVING 搜索条件可以在分组操作之前应⽤,那么它就会在分组之前应⽤。查询优化器可能⽆法识别所有可以在分组操作之前应⽤的 HAVING 搜索条件。建议将所有这些搜索条件放在 WHERE ⼦句中,⽽不是 HAVING ⼦句中。
(2)使⽤inner join语句
SELECT cust_name, SUM(item_price*quantity) AS total_price
FROM Customers
INNER JOIN Orders ON Customers.cust_id = Orders.cust_id
INNER JOIN OrderItems der_num = der_num
GROUP BY cust_name
HAVING SUM(item_price*quantity) >= 1000
ORDER BY cust_name;
SELECT cust_name, SUM(item_price*quantity) AS total_price
FROM OrderItems
INNER JOIN orders der_num = der_num
INNER JOIN customers ON Customers.cust_id = Orders.cust_id
GROUP BY cust_name
HAVING SUM(item_price*quantity) >= 1000
ORDER BY cust_name;
我在这⾥列出了两段代码,他们的运⾏结果完全相同,不同点在于inner join⼦句中三个表的顺序不同,三个表的顺序与on后边的句⼦相互依赖,⼀定要注意
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论