我使用Access查询设计器来设置连接,但它在VBA中不起作用 我在FROM' -2147217900(80040e14)'
中收到语法错误Set Signal = cnn.Execute("SELECT Table2.W, Table5.Attribute " _
& " FROM (((((Table7 " _
& " INNER JOIN Table5 )" _
& " INNER JOIN Table6) " _
& " INNER JOIN Table1) " _
& " INNER JOIN Table2 " _
& " ON Table1.DB_ID = Table2.Attrib_Def) " _
& " INNER JOIN Table4 " _
& " ON Table2.Opt_Obj_ID = Table4.Signal " _
& " AND Table2.Object_ID = Table4.Node " _
& " ON Table6.DB_ID = Table4.Signal) " _
& " INNER JOIN Table3 " _
& " ON Table4.Node = Table3.Node " _
& " ON Table5.DB_ID = Table3.Node" _
& " ON Table7.DB_ID = Table3.Message " _
& " WHERE (((Table1.Name)='TypeA') " _
& " AND ((Table7.Name)='XX') " _
& " AND ((Table6.Name)='X')) ")
答案 0 :(得分:2)
解决这类问题的最佳方法是将生成的字符串发送到调试/即时窗口:
Sub test()
Sql = "SELECT Table2.W, Table5.Attribute " _
& " FROM (((((Table7 " _
& " INNER JOIN Table5 )" _
& " INNER JOIN Table6) " _
& " INNER JOIN Table1) " _
& " INNER JOIN Table2 " _
& " ON Table1.DB_ID = Table2.Attrib_Def) " _
& " INNER JOIN Table4 " _
& " ON Table2.Opt_Obj_ID = Table4.Signal " _
& " AND Table2.Object_ID = Table4.Node " _
& " ON Table6.DB_ID = Table4.Signal) " _
& " INNER JOIN Table3 " _
& " ON Table4.Node = Table3.Node " _
& " ON Table5.DB_ID = Table3.Node" _
& " ON Table7.DB_ID = Table3.Message " _
& " WHERE (((Table1.Name)='TypeA') " _
& " AND ((Table7.Name)='XX') " _
& " AND ((Table6.Name)='X')) "
Debug.Print Sql
End Sub
复制出你运行时产生的sql并转到文本编辑器,这样你就可以正确地缩进这个混乱:
SELECT Table2.W, Table5.Attribute
FROM
(
(
(
(
(
Table7 INNER JOIN Table5
)
INNER JOIN Table6
)
INNER JOIN Table1
)
INNER JOIN Table2
ON Table1.DB_ID = Table2.Attrib_Def
)
INNER JOIN Table4
ON Table2.Opt_Obj_ID = Table4.Signal
AND Table2.Object_ID = Table4.Node
ON Table6.DB_ID = Table4.Signal
)
INNER JOIN Table3
ON Table4.Node = Table3.Node
ON Table5.DB_ID = Table3.Node
ON Table7.DB_ID = Table3.Message
WHERE
(
(
(
Table1.Name
) ='TypeA'
)
AND
(
(
Table7.Name
)='XX'
)
AND
(
(
Table6.Name
)='X'
)
)
用于生成SQL的Access的GUI就是它在括号中变得愚蠢。在这种情况下,不需要单个括号。我在这里看不到任何超级的东西,但它的丑陋和难以诊断正在发生的事情。而是使用:
SELECT Table2.W, Table5.Attribute
FROM Table7
INNER JOIN Table3
ON Table3.Message = Table3.DB_ID
INNER JOIN Table5
ON Table5.DB_ID = Table3.Node
INNER JOIN Table4
ON Table4.Node = Table3.Node
INNER JOIN Table6
ON Table6.DB_ID = Table4.Signal
INNER JOIN Table2
ON Table2.Opt_Obj_ID = Table4.Signal
INNER JOIN Table1
ON Table1.DB_ID = Table2.Attrib_Def
WHERE
Table1.Name ='TypeA' AND
Table7.Name = 'XX' AND
Table6.Name = 'X';
这更清晰,更容易理解。我们能够删除所有这些parantheses的原因是因为它只有INNER JOIN
而WHERE
语句都是'ANDs'。如果那里有一些OR
或LEFT OUTER JOIN
,那么我们必须更加司法化,但我可以向你保证,Access会在那里留下太多括号。它只是爱他们。
无论如何将它放回VBA你可以使用:
Sub test()
...all your existing code...
Dim sql As String
sql = "SELECT Table2.W, Table5.Attribute"
sql = sql & " FROM Table7"
sql = sql & " INNER JOIN Table3"
sql = sql & " ON Table3.Message = Table3.DB_ID"
sql = sql & " INNER JOIN Table5"
sql = sql & " ON Table5.DB_ID = Table3.Node"
sql = sql & " INNER JOIN Table4"
sql = sql & " ON Table4.Node = Table3.Node"
sql = sql & " INNER JOIN Table6"
sql = sql & " ON Table6.DB_ID = Table4.Signal"
sql = sql & " INNER JOIN Table2"
sql = sql & " ON Table2.Opt_Obj_ID = Table4.Signal"
sql = sql & " INNER JOIN Table1"
sql = sql & " ON Table1.DB_ID = Table2.Attrib_Def"
sql = sql & " WHERE"
sql = sql & " Table1.Name ='TypeA' AND"
sql = sql & " Table7.Name = 'XX' AND"
sql = sql & " Table6.Name = 'X';"
Set Signal = cnn.Execute(sql)
End Sub
最后,无法保证删除括号内容会有所帮助,但它肯定会消除一些歧义并帮助您诊断出它没有正确执行的原因。