使用VB Concatenate函数时参数错误

时间:2014-05-08 15:22:53

标签: sql vba ms-access access-vba

我使用了以下来自朋友的VBA,它可以很好地连接MS Access中的项目。

   
 Public Function ConcatRelated(strField As String, _
    strTable As String, _
    Optional strWhere As String, _
    Optional strOrderBy As String, _
    Optional strSeparator = ", ") As Variant
On Error GoTo Err_Handler
    'Purpose:   Generate a concatenated string of related records.
    'Return:    String variant, or Null if no matches.
    'Arguments: strField = name of field to get results from and concatenate.
    '           strTable = name of a table or query.
    '           strWhere = WHERE clause to choose the right values.
    '           strOrderBy = ORDER BY clause, for sorting the values.
    '           strSeparator = characters to use between the concatenated values.
    'Notes:     1. Use square brackets around field/table names with spaces or odd characters.
    '           2. strField can be a Multi-valued field (A2007 and later), but strOrderBy cannot.
    '           3. Nulls are omitted, zero-length strings (ZLSs) are returned as ZLSs.
    '           4. Returning more than 255 characters to a recordset triggers this Access bug:
    '               http://allenbrowne.com/bug-16.html
    Dim rs As DAO.Recordset         'Related records
    Dim rsMV As DAO.Recordset       'Multi-valued field recordset
    Dim strSql As String            'SQL statement
    Dim strOut As String            'Output string to concatenate to.
    Dim lngLen As Long              'Length of string.
    Dim bIsMultiValue As Boolean    'Flag if strField is a multi-valued field.

    'Initialize to Null'
    ConcatRelated = Null

    'Build SQL string, and get the records.
    strSql = "SELECT " & strField & " FROM " & strTable
    If strWhere <> vbNullString Then
        strSql = strSql & " WHERE " & strWhere
    End If
    If strOrderBy <> vbNullString Then
        strSql = strSql & " ORDER BY " & strOrderBy
    End If
    Set rs = DBEngine(0)(0).OpenRecordset(strSql, dbOpenDynaset)
    'Determine if the requested field is multi-valued (Type is above 100.)
    bIsMultiValue = (rs(0).Type > 100)

    'Loop through the matching records
    Do While Not rs.EOF
        If bIsMultiValue Then
            'For multi-valued field, loop through the values
            Set rsMV = rs(0).Value
            Do While Not rsMV.EOF
                If Not IsNull(rsMV(0)) Then
                    strOut = strOut & rsMV(0) & strSeparator
                End If
                rsMV.MoveNext
            Loop
            Set rsMV = Nothing
        ElseIf Not IsNull(rs(0)) Then
            strOut = strOut & rs(0) & strSeparator
        End If
        rs.MoveNext
    Loop
    rs.Close

    'Return the string without the trailing separator.
    lngLen = Len(strOut) - Len(strSeparator)
    If lngLen > 0 Then
        ConcatRelated = Left(strOut, lngLen)
    End If

Exit_Handler:
    'Clean up
    Set rsMV = Nothing
    Set rs = Nothing
    Exit Function

Err_Handler:
    MsgBox "Error " & Err.Number & ": " & Err.Description, vbExclamation, "ConcatRelated()"
    Resume Exit_Handler
End Function

我通过以下查询成功调用此函数:

INSERT INTO tblData ( SubjectNumber, RECDATE, RecordedDoses, DoseTimes, FoodType, ProgrammingComments )
SELECT d.SubjectNumber, d.RECDATE, Count(d.RECTIME) AS RecordedDoses, ConcatRelated("RECTIME", "qryDump2", "SubjectNumber= """ & d.[SubjectNumber]  & """"  & " AND RECDATE=" & FORMAT(d.RECDATE, "\#yyyy-m-d\#")) AS DoseTimes, ConcatRelated("FoodType", "qryDump2", "SubjectNumber= """ & d.[SubjectNumber]  & """"  & " AND RECDATE=" & FORMAT(d.RECDATE, "\#yyyy-m-d\#")) AS FoodType, d.Visit AS ProgrammingComments
FROM qryDump2 AS d
GROUP BY d.SubjectNumber, d.RECDATE, d.Visit
HAVING Count(d.RECTIME)<2 Or Count(d.RECTIME)>2
ORDER BY d.RECDATE;

上面的查询引用了几个表和查询。问题是,当我的标准是特定主题时,例如, &#34; 1011002&#34;,连接函数运行没有问题。但是,当标准是其他任何条件时,例如提示标准,引用文本框等,我得到了乐趣&#34;错误3061:参数太少。预期1.如果我将我的标准切换回字符串,例如&#34; 1011002&#34;它又有效了。使用提示条件时,如果我输入相同的项目,即1011002,则会再次出现错误。

我错过了什么?

编辑:在引用我上面提到的标准的行中称为几个项目的查询如下:

SELECT tblDump.SubjectNumber, IIf(tblDump.SD_DAY=1,tblDump.RECDATE,tblDump.RECDATE-1) AS RECDATE, IIf(tblDump.DRUG_Q1=1,tblDump.RECTIME,tblDump.DRUG_Q6) AS RECTIME, tblDump.FoodType, IIf(IIf(tblDump.SD_DAY=1,tblDump.RECDATE,tblDump.RECDATE-1)=tblL.DiscontDate,"DayOfDiscontinuation",IIf(IIf(tblDump.SD_DAY=1,tblDump.RECDATE,tblDump.RECDATE-1)=tblL.CompletionDate,"CompletionDate",IIf(IIf(tblDump.SD_DAY=1,tblDump.RECDATE,tblDump.RECDATE-1)=tblL.[2],"Visit2"))) AS Visit
FROM tblDump LEFT JOIN tblL ON tblDump.SubjectNumber = tblL.SubjectNumber
WHERE tblDump.SubjectNumber=Forms![frm]![test];

where语句,当我使用实际值时,例如&#34; 1011002&#34; (主题编号是文本而不是数字,即使我给出的例子是数字),连接函数也可以。当我使用上面的内容,即引用表单字段时,我得到上述错误。

1 个答案:

答案 0 :(得分:0)

where子句不检查文本是否有空格,可能在将表单数据放入函数调用之前修剪表单数据,看看是否会阻止代码在sql中创建空where子句。 / p>