连接表后得到错误的值 - MySQL - PHP

时间:2012-09-24 05:50:37

标签: php mysql sql join

我必须使用4个表生成一个报告,我尝试了很多连接,但是我得到了错误的值:(

希望有人能帮助我。

StaffAssign表:

----------------------------
| Tid | StaffId | Planned  |
----------------------------
| 123 |   2     | 10:00:00 |
| 123 |   4     | 05:00:00 |
| 124 |   2     | 09:00:00 |
----------------------------

ActualEffort表:

--------------------------------------------
| Tid | StaffId | ActualEffort  | logdate  |
--------------------------------------------
| 123 |   2     | 05:00:00      |2012-09-01|
| 123 |   4     | 05:00:00      |2012-09-01|
| 123 |   2     | 06:00:00      |2012-09-03|
| 124 |   2     | 09:00:00      |2012-09-04|
--------------------------------------------

ProjectList表:

-------------------
| ProjectId | Tid |
-------------------
|    1      | 123 |
|    2      | 124 |
-------------------

ProjectName表:

-------------------
| Id  | name      |
-------------------
| 1   | project1  |
| 2   | project2  |
-------------------

以下是我正在使用的查询:

SELECT P.id AS projectid,P.name,
SEC_TO_TIME(SUM(TIME_TO_SEC(A.planned)))planned,SEC_TO_TIME(SUM(TIME_TO_SEC(E.actualeffort)))actual FROM actualeffort E 
INNER JOIN staffassign A ON A.tid = E.tid
INNER JOIN projectlist L ON L.tid = A.tid
INNER JOIN projectname P ON P.id = L.projectid 
WHERE E.logdate BETWEEN FROM_UNIXTIME('1346475600') AND FROM_UNIXTIME('1348290000')
GROUP BY P.id

我得到了这个:

---------------------------------------------
| projectid | name     | planned | actual   |
---------------------------------------------
|     1     | project1 | 15:00:00| 12:00:00 |
|     2     | project2 | 09:00:00| 09:00:00 |
---------------------------------------------

但它应该是这样的:

---------------------------------------------
| projectid | name     | planned | actual   |
---------------------------------------------
|     1     | project1 | 15:00:00| 16:00:00 |
|     2     | project2 | 09:00:00| 09:00:00 |
---------------------------------------------

我很困惑,我不知道连接哪里出错了。

有人请帮助我,我很震惊。

3 个答案:

答案 0 :(得分:2)

WHERE过滤器可能有误。请注意,条件中的第一个日期时间从'08:00:00'开始 -

SELECT FROM_UNIXTIME('1346475600') dt1, FROM_UNIXTIME('1348290000') dt2;
+---------------------+---------------------+
| dt1                 | dt2                 |
+---------------------+---------------------+
| 2012-09-01 08:00:00 | 2012-09-22 08:00:00 |
+---------------------+---------------------+

ActualEffortlogdate字段的类型为DATE;值'2012-09-01'小于'2012-09-01 08:00:00'。因此,请更改此条件或使用DATE函数 -

WHERE
  E.logdate BETWEEN
  DATE(FROM_UNIXTIME('1346475600')) AND DATE(FROM_UNIXTIME('1348290000'))

(适用编辑)

首先,当您仅在StaffAssign列加入ActualEffortTid时,您会获得一个迷你 - Tid=123特别是Tid,因为两个表都包含多个具有StaffAssign的行,并且没有其他特定条件可以在行之间建立1:1或最多1:N的关系。

但事实上,1:N也不会这样做:虽然它不会给你笛卡尔积的效果,但它会导致一方的重复值,结果是一个扭曲的SUM。

因此,ActualEffortSELECT pl.ProjectId, pn.name, sa.Planned, ae.ActualEffort FROM ProjectList pl JOIN ProjectName pn ON pn.Id = pl.ProjectId LEFT JOIN (SELECT Tid, SEC_TO_TIME(SUM(TIME_TO_SEC(Planned))) Planned FROM StaffAssign GROUP BY Tid) sa ON sa.Tid = pl.Tid LEFT JOIN (SELECT Tid, SEC_TO_TIME(SUM(TIME_TO_SEC(ActualEffort))) ActualEffort FROM ActualEffort GROUP BY Tid) ae ON ae.Tid = pl.Tid GROUP BY ProjectId; 中的数据必须单独汇总,然后加入,如下所示:

{{1}}

答案 1 :(得分:1)

您的SQL中存在错误: 你不想加入p.ProjectID而不是p.id

答案 2 :(得分:0)

尝试此查询

SELECT P.id AS projectid,P.name,
SEC_TO_TIME(SUM(TIME_TO_SEC(A.planned)))planned,SEC_TO_TIME(SUM(TIME_TO_SEC(E.actualeffort)))actual FROM actualeffort E 
INNER JOIN staffassign A ON A.tid = E.tid
INNER JOIN projectlist L ON L.tid = A.tid
INNER JOIN projectlist L ON L.tid = E.tid        // you have not added this line
INNER JOIN projectname P ON P.id = L.projectid 
WHERE E.logdate BETWEEN FROM_UNIXTIME('1346475600') AND FROM_UNIXTIME('1348290000')
GROUP BY P.id

LE之间的联接应该存在。