访问内部联接的问题

时间:2013-07-02 16:03:01

标签: sql ms-access

我在这个特定的语句中一直收到语法错误。

SELECT tbl1.ProjectID, tbl1.EntryDate AS StartDate, tbl2.EntryDate AS EndDate, 
(tbl3.ChecklistDayMax - tbl3.ChecklistDayMin + 1) AS DaysAllotted, 
(SELECT ProjectPriority FROM project_master WHERE ProjectID = tbl1.ProjectID) AS Priority,
tbl3.MilestoneName,
IIF(Priority = 1, tbl3.BonusDaysFH, 
IIF(Priority = 2, tbl3.BonusDaysFM, 
IIF(Priority = 3, tbl3.BonusDaysFL))) AS BonusDaysAllotted
FROM (((checklist_entries AS tbl1
INNER JOIN checklist_entries AS tbl2 ON tbl1.ProjectID = tbl2.ProjectID)
INNER JOIN milestone_def AS tbl3 ON [@milestoneID] = milestone_def.MilestoneDefID)
INNER JOIN project_active_status AS tbl4 ON tbl1.ProjectID = project_active_status.ProjectID)
WHERE tbl1.ChecklistDay = tbl3.ChecklistDayMin
AND tbl2.ChecklistDay = tbl3.ChecklistDayMax
AND tbl4.ProjectIsOpen = FALSE;

错误显示连接操作中的语法错误,然后在第二个INNER JOIN之后突出显示milestone_def。有趣的是,如果我改变这条线......

INNER JOIN milestone_def AS tbl3 ON [@milestoneID] = milestone_def.MilestoneDefID)

用这条线......

INNER JOIN milestone_def AS tbl3 ON [@milestoneID] = tbl3.MilestoneDefID)

我收到错误不支持加入表达式,然后突出显示...

[@milestoneID] = tbl3.MilestoneDefID)

但正如你所看到的,在第一次加入......

INNER JOIN checklist_entries AS tbl2 ON tbl1.ProjectID = tbl2.ProjectID

我将它命名为tbl2,然后使用tbl2.ProjectID,表达式就可以了。最终,无论我如何命名这些东西,我都需要让它发挥作用。

[@ milestoneID]是传递给查询以匹配milestone_def.MilestoneDefID的参数

3 个答案:

答案 0 :(得分:1)

由于问题在于连接,因此使用更简单的查询来研究问题是明智的。

SELECT *
FROM
    ((checklist_entries AS tbl1
    INNER JOIN checklist_entries AS tbl2
    ON tbl1.ProjectID = tbl2.ProjectID)
    INNER JOIN milestone_def AS tbl3
    ON [@milestoneID] = milestone_def.MilestoneDefID)
    INNER JOIN project_active_status AS tbl4
    ON tbl1.ProjectID = project_active_status.ProjectID

请注意,您已将表名别名。因此,您必须使用这些别名而不是ON子句中的表名。

SELECT *
FROM
    ((checklist_entries AS tbl1
    INNER JOIN checklist_entries AS tbl2
    ON tbl1.ProjectID = tbl2.ProjectID)
    INNER JOIN milestone_def AS tbl3
    ON tbl1.[@milestoneID] = tbl3.MilestoneDefID)
    INNER JOIN project_active_status AS tbl4
    ON tbl1.ProjectID = tbl4.ProjectID

我不知道[@milestoneID]是什么或来自哪里。我最好的猜测是checklist_entries中的字段,因此我使用tbl1别名对其进行了限定。

答案 1 :(得分:1)

[扩展自评论。]这只是一种预感,因为我无权访问Access(哈哈),但您的查询当前指定的INNER JOIN实际上并未将表与其余的查询:

... 
INNER JOIN milestone_def AS tbl3
ON [@milestoneID] = milestone_def.MilestoneDefID
...

ON子句仅引用外部变量,因此与JOIN操作无关,使其有效CROSS JOIN WHERE条件:< / p>

... 
CROSS JOIN milestone_def AS tbl3
...
WHERE [@milestoneID] = milestone_def.MilestoneDefID
...

查看查询的底部,您可以在WHERE子句中获得此表的实际连接条件;这些应该交换到ON子句,以便它实际指定INNER JOIN条件:

... 
INNER JOIN milestone_def AS tbl3
ON tbl1.ChecklistDay = tbl3.ChecklistDayMin
AND tbl2.ChecklistDay = tbl3.ChecklistDayMax
...
WHERE [@milestoneID] = milestone_def.MilestoneDefID
...

这种方式肯定更合乎逻辑,它可能解决问题Access的解析器正在理解您的查询。

答案 2 :(得分:-1)

我认为HansUp的回答指向了正确的方向。我注意到的另一件事是你有一系列三个嵌套的IIF,最后一个只有一个测试和一个true但是缺少false参数。我认为这三个都是强制性的。