2014-03-13 140 views
2

所以我曾经有10个查询,相同的SELECT语句,不同的WHERE。一个查询是这样的:MYSQL查询,其中SELECT语句(要多行/ where语句)

SELECT 
    workdate AS `Date`, 
    DAYNAME(workdate) AS `Day`, 
    COALESCE(TRUNCATE(SUM((CASE 
        WHEN 
         paycode = '03 Overtime 2.0' 
        then 
         (IF(historyemployeepay.`Other Rate` = 0, 
          (employeehours * (historyemployeepay.`Base Rate` * 2.0)), 
          (employeehours * (historyemployeepay.`Other Rate` * 2.0)))) 
        WHEN paycode = '01 Ordinary' then (employeehours * historyemployeepay.`Base Rate`) 
        WHEN 
         paycode = '02 Overtime 1.5' 
          OR paycode = '03 Overtime 2.0' 
        then 
         (IF(historyemployeepay.`Other Rate` = 0, 
          (employeehours * (historyemployeepay.`Base Rate` * 1.5)), 
          (employeehours * (historyemployeepay.`Other Rate` * 1.5)))) 
       end)), 
       2), 
      0) AS `Amount` 
FROM 
    otherrates, 
    employeedata 
     INNER JOIN 
    employeehours ON employeedata.`ID Number` = employeehours.employeeid 
     JOIN 
    historyemployeepay ON employeehours.employeeid = historyemployeepay.EmployeeID 
WHERE 
    shift = 'PM' AND DriverDock = 'Driv' 
     AND `Salary Code Description` LIKE '%Perm%' 
     AND DAYNAME(workdate) <> 'Saturday' 
     AND historyemployeepay.FromDate <= employeehours.workdate 
     AND (historyemployeepay.ToDate IS NULL 
     OR employeehours.workdate <= historyemployeepay.ToDate) 
GROUP BY workdate 

我想有他们所有网站页面上,如果我这样做单独的网站页面需要年龄加载...所以我想到了一个好主意的尝试将它们链接在一起,如下所示。请注意我在SELECT语句中取出了八行,仅留下了两个例子。

我该如何得到这个工作?它不显示正确的值(空),我做错了什么?

SELECT 
    workdate AS `Date`, 
    DAYNAME(workdate) AS `Day`, 
    (CASE 
     WHEN 
      shift = 'AM' AND DriverDock = 'Driv' 
       AND `Salary Code Description` LIKE '%Perm%' 
     then 
      COALESCE(TRUNCATE(SUM((CASE 
          WHEN 
           paycode = '03 Overtime 2.0' 
          then 
           (IF(historyemployeepay.`Other Rate` = 0, 
            (employeehours * (historyemployeepay.`Base Rate` * 2.0)), 
            (employeehours * (historyemployeepay.`Other Rate` * 2.0)))) 
          WHEN paycode = '01 Ordinary' then (employeehours * historyemployeepay.`Base Rate`) 
          WHEN 
           paycode = '02 Overtime 1.5' 
            OR paycode = '03 Overtime 2.0' 
          then 
           (IF(historyemployeepay.`Other Rate` = 0, 
            (employeehours * (historyemployeepay.`Base Rate` * 1.5)), 
            (employeehours * (historyemployeepay.`Other Rate` * 1.5)))) 
         end)), 
         2), 
        0) 
    end) AS `AMPERMDRIV`, 
    (CASE 
     WHEN 
      shift = 'AM' AND DriverDock = 'Dock' 
       AND `Salary Code Description` LIKE '%Perm%' 
     then 
      COALESCE(TRUNCATE(SUM((CASE 
          WHEN 
           paycode = '03 Overtime 2.0' 
          then 
           (IF(historyemployeepay.`Other Rate` = 0, 
            (employeehours * (historyemployeepay.`Base Rate` * 2.0)), 
            (employeehours * (historyemployeepay.`Other Rate` * 2.0)))) 
          WHEN paycode = '01 Ordinary' then (employeehours * historyemployeepay.`Base Rate`) 
          WHEN 
           paycode = '02 Overtime 1.5' 
            OR paycode = '03 Overtime 2.0' 
          then 
           (IF(historyemployeepay.`Other Rate` = 0, 
            (employeehours * (historyemployeepay.`Base Rate` * 1.5)), 
            (employeehours * (historyemployeepay.`Other Rate` * 1.5)))) 
         end)), 
         2), 
        0) 
    end) AS `AMPERMDOCK` 
FROM 
    otherrates, 
    employeedata 
     INNER JOIN 
    employeehours ON employeedata.`ID Number` = employeehours.employeeid 
     JOIN 
    historyemployeepay ON employeehours.employeeid = historyemployeepay.EmployeeID 
WHERE 
    DAYNAME(workdate) <> 'Saturday' 
     AND historyemployeepay.FromDate <= employeehours.workdate 
     AND (historyemployeepay.ToDate IS NULL 
     OR employeehours.workdate <= historyemployeepay.ToDate) 
GROUP BY workdate 

看一看结果:

enter image description here

+0

为什么对SUM集合外部的'shift','DriverDock'进行条件测试? ......是否真的想要评估那些聚合后的人? (对我来说不正确)。在评估可能返回NULL的CASE后,为什么没有执行COALESCE和TRUNCATE?为什么对'otherrates'表的CROSS JOIN操作,它是否只包含一行,以及为什么连接的逗号语法?给这些表分配简短的别名可以使合格的列引用更短,并且许多列引用不合格,我们无法确定这些列来自哪个表; – spencer7593

+0

为什么第二次测试'03加班2.0',这已经在早些时候被抓到了? – spencer7593

回答

1

的CASE表达式有一个隐含的ELSE NULL,而你没有COALESCE捕捉NULL上最CASE。

在聚合计算后,未包含在GROUP BY中的非聚合的评估看起来不正确;看起来会返回“错误”的结果。

我想你想要更多的东西是这样的:

SELECT h.workdate AS `Date` 
    , DAYNAME(h.workdate) AS `Day` 
    , COALESCE(TRUNCATE(SUM(
     CASE 
     WHEN (shift="AM" AND DriverDock = 'Driv' AND `Salary Code Description` LIKE '%Perm%') 
      THEN 
      CASE 
      WHEN paycode IN ('03 Overtime 2.0') 
       THEN (employeehours * IF(p.`Other Rate`=0,p.`Base Rate`,p.`Other Rate`) * 2.0) 
      WHEN paycode IN ('02 Overtime 1.5') 
       THEN (employeehours * IF(p.`Other Rate`=0,p.`Base Rate`,p.`Other Rate`) * 1.5) 
      WHEN paycode IN ('01 Ordinary') 
       THEN (employeehours * p.`Base Rate`) 
      END 
     END 
     ),2),0) AS `AMPERMDRIV` 
    , COALESCE(TRUNCATE(SUM(
     CASE 
     WHEN (shift="AM" AND DriverDock = 'Dock' AND `Salary Code Description` LIKE '%Perm%') 
      THEN 
      CASE 
      WHEN paycode IN ('03 Overtime 2.0') 
       THEN (employeehours * IF(p.`Other Rate`=0,p.`Base Rate`,p.`Other Rate`) * 2.0) 
      WHEN paycode IN ('02 Overtime 1.5') 
       THEN (employeehours * IF(p.`Other Rate`=0,p.`Base Rate`,p.`Other Rate`) * 1.5) 
      WHEN paycode IN ('01 Ordinary') 
       THEN (employeehours * p.`Base Rate`) 
      END 
     END 
     ),2),0) AS `AMPERMDOCK` 
    FROM employeedata d 
    JOIN employeehours h 
    ON d.`ID Number` = h.employeeid 
    JOIN historyemployeepay p 
    ON (h.employeeid = p.EmployeeID) 
    AND (h.workdate >= p.FromDate) 
    AND (h.workdate <= p.ToDate OR p.ToDate IS NULL) 
CROSS 
    JOIN otherrates r 
WHERE DAYNAME(h.workdate) <> 'Saturday' 
GROUP BY h.workdate 

我会将所有的列引用,如果我知道的柱子来自哪个表。

+0

谢谢斯宾塞,那很完美。我还有一个问题,也许你可以帮忙?请看看这个问题:http://stackoverflow.com/questions/22394073/mysql-query-convert-row-to-columns-with-complex-query – atomapps