【问题标题】:Is there a better way to write this code without having to use so many table queries?有没有更好的方法来编写这段代码而不必使用那么多表查询?
【发布时间】:2022-11-28 22:09:51
【问题描述】:

我是这个编码爱好者的新手,不想告诉你我花了多长时间才得到下面的输出……它确实做了我想要的,但我确信必须有更有效的方法来实现它,我花了那么长时间现在虽然我看不到其他任何东西!


WITH

Italian_Sales as(
 SELECT sum(od.quantityOrdered) as total_it, od.productCode as product_it
   FROM orderdetails as od
   JOIN orders as o
 ON od.orderNumber = o.orderNumber
   JOIN customers as c
     ON o.customerNumber = c.customerNumber
   JOIN products as p
     ON p.productCode = od.productCode
  WHERE c.country in ("Italy")
  GROUP BY product_it
),

Spanish_Sales as(
 SELECT sum(od.quantityOrdered) as total_sp, od.productCode as product_sp
   FROM orderdetails as od
   JOIN orders as o
 ON od.orderNumber = o.orderNumber
   JOIN customers as c
     ON o.customerNumber = c.customerNumber
   JOIN products as p
     ON p.productCode = od.productCode
  WHERE c.country in ("Spain")
  GROUP BY product_sp
),

French_Sales as(
 SELECT sum(od.quantityOrdered) as total_fr, od.productCode as product_fr
   FROM orderdetails as od
   JOIN orders as o
 ON od.orderNumber = o.orderNumber
   JOIN customers as c
     ON o.customerNumber = c.customerNumber
   JOIN products as p
     ON p.productCode = od.productCode
  WHERE c.country in ("France")
  GROUP BY product_fr
),

UK_Sales as(
 SELECT sum(od.quantityOrdered) as total_uk, od.productCode as product_uk
   FROM orderdetails as od
   JOIN orders as o
 ON od.orderNumber = o.orderNumber
   JOIN customers as c
     ON o.customerNumber = c.customerNumber
   JOIN products as p
     ON p.productCode = od.productCode
  WHERE c.country in ("UK")
  GROUP BY product_uk
),

Total_Sales as(
 SELECT sum(od.quantityOrdered) as total_sales, od.productCode as product_total
   FROM orderdetails as od
   JOIN orders as o
 ON od.orderNumber = o.orderNumber
   JOIN customers as c
     ON o.customerNumber = c.customerNumber
   JOIN products as p
     ON p.productCode = od.productCode
  WHERE c.country in ("Spain", "France", "UK", "Italy")
  GROUP BY product_total
)

SELECT p.productCode, p.productLine, p.productName, ts.total_sales as "Total Sales", its.total_it as    "Italian Sales", 
       ss.total_sp as "Spanish Sales", fs.total_fr as "French Sales", us.total_uk as "UK Sales"
  FROM products as p
  LEFT JOIN Italian_Sales as its
    ON p.productCode = product_it 
  LEFT JOIN Spanish_Sales as ss
    ON p.productCode = product_sp
  LEFT JOIN French_Sales as fs
    ON p.productCode = product_fr
  LEFT JOIN UK_Sales as us
    ON p.productCode = product_uk
  LEFT JOIN Total_Sales as ts
    ON p.productCode = product_total
 GROUP BY p.productCode
 ORDER BY ts.total_sales DESC;

所需的输出低于每个国家/地区的销售额和总金额,但在适用的情况下也显示空值(这是我花了很长时间才记得离开加入的原因)

enter image description here

【问题讨论】:

  • 这将是PIVOT的一个很好的候选人
  • 而不是所有单独的、几乎相同的查询,只需将国家/地区包含在一个查询的分组依据中(如果需要限制国家/地区,则可以在这些国家/地区添加 WHERE 子句过滤器)

标签: sql optimization


【解决方案1】:

这是一个非常标准的PIVOT,特别是考虑到聚合,但是您可以使用更简单的方法...SUM(CASE)

除了过滤器之外,您的所有子查询都是相同的,因此我们可以使用过滤器作为 CASE 语句的条件,并可以返回我们想要计算的值只要当行匹配筛选条件并为所有其他记录返回零或空值时。所以我们用一个单独的CASE替换每个子查询:

SELECT p.productCode, p.productLine, p.productName
     , SUM(od.quantityOrdered) AS [Total Sales]
     , SUM(CASE c.country WHEN 'Italy' THEN od.quantityOrdered END) AS [Italian Sales]
     , SUM(CASE c.country WHEN 'Spain' THEN od.quantityOrdered END) AS [Spanish Sales]
     , SUM(CASE c.country WHEN 'France' THEN od.quantityOrdered END) AS [French Sales]
     , SUM(CASE c.country WHEN 'UK' THEN od.quantityOrdered END) AS [UK Sales]
FROM products p
LEFT OUTER JOIN orderdetails od ON p.productCode = od.productCode
LEFT OUTER JOIN orders o ON od.orderNumber = o.orderNumber
LEFT OUTER JOIN customers c ON o.customerNumber = c.customerNumber
GROUP BY p.productCode, p.productLine, p.productName

当您开始获得太多术语时,实际的 PIVOT 查询可能会更简单,但目前这是非常易于管理的。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-03-14
    • 2023-03-28
    相关资源
    最近更新 更多