【问题标题】:SQL - Finding parts that were ordered by a customer who ordered more than 2 distinct partsSQL - 查找订购超过 2 个不同零件的客户订购的零件
【发布时间】:2015-05-02 06:12:27
【问题描述】:

我有 4 张桌子:

  • 客户:cno(主键)、cname、街道、邮编、电话
  • 订单:ono(主键)、cno(外键)、wno(外键)、收货、发货
  • 详细信息:ono(外键)、pno(外键)、数量、费用
  • parts:pno(主键)、pname、qoh、price、olevel

我正在尝试查找订购两个以上不同零件的客户订购的零件的名称。 This 线程的相关性最接近,对我有很大帮助,但我在运行修改后的查询时遇到了问题,该查询如下并返回 null:

SELECT p.pname
FROM parts p
INNER JOIN odetails d ON p.pno=d.pno
INNER JOIN orders o ON d.ono=o.ono
INNER JOIN customers c ON o.cno=c.cno
GROUP BY p.pname, c.cname
HAVING COUNT(DISTINCT p.pno)>2;

任何帮助将不胜感激。

【问题讨论】:

  • 在继续尝试使查询正常工作之前,您确实应该决定您的数据库。 Oracle、SQL Server 和 MySQL 是三种不同的数据库引擎。请适当地标记问题。
  • 显示你的测试数据集。
  • 这个命名策略太气人了。我要传递这个。

标签: mysql sql sql-server oracle


【解决方案1】:

改变

GROUP BY p.pname, c.cname

GROUP BY c.cname

如果您按p.pname 分组,则COUNT(DISTINCT p.pno) 将始终返回1 除非两个pno 具有相同的pname

【讨论】:

  • 这行不通,因为您不能在 GROUP BY 中拥有不在 SELECT 中的列 - 您将获得 ORA-00979: not a GROUP BY expression
  • 在 MySQL 上,您可以 GROUP BY 一个在 SELECT 子句中不存在的表达式。 OP 正在使用哪个 DB 存在歧义,但是,他声明他的查询返回 NULL,而不是抛出错误。如果您查看他的查询,您会发现他在GROUP BY 中有c.cname,但在SELECT 中没有,这导致我假设MySQL。我不确定 sql-server 或 oracle 是如何处理这个问题的。
【解决方案2】:

我假设您使用的是 Oracle,因为 your other question using the same tables for a different query 是一个 Oracle 问题。

需要考虑的一些事情。是否可以有多个客户订购两个以上不同的零件?如果是这样,您是否希望将客户姓名连同订购的零件一起退回?首先,获取订购了两个以上不同零件的所有客户:

SELECT c.cno
  FROM customers c INNER JOIN orders o
    ON c.cno = o.cno
 INNER JOIN odetails od
    ON o.ono = od.ono
 GROUP BY c.cno
HAVING COUNT(DISTINCT od.pno) > 2;

然后得到他们订购的零件:

WITH c1 AS (
    SELECT c.cno
      FROM customers c INNER JOIN orders o
        ON c.cno = o.cno
     INNER JOIN odetails od
        ON o.ono = od.ono
     GROUP BY c.cno
    HAVING COUNT(DISTINCT od.pno) > 2
)
SELECT p.pno, p.pname, COUNT(*)
  FROM parts p INNER JOIN odetails od
    ON p.pno = od.pno
 INNER JOIN orders o
    ON od.ono = o.ono
 INNER JOIN c1
    ON o.cno = c1.cno
 GROUP BY p.pno, p.pname;

顺便说一句,您应该考虑@Strawberry 的评论。你的表名很好,但你的列名真的很可怕。 Oracle 为您提供 30 个字符的对象名称;使用它们。例如,没有理由将列命名为 pno,而不是 product_id

【讨论】:

    猜你喜欢
    • 2021-01-05
    • 1970-01-01
    • 2010-10-09
    • 1970-01-01
    • 1970-01-01
    • 2016-03-11
    • 2023-03-11
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多