8

专家交流teck 共和国有一些 关于使用 combobox.recordset 属性在 Access 表单中填充组合框的文献。

这些控件通常在控件的“行源”属性中填充“SELECT *”字符串,引用应用程序客户端上可用的表或查询。当我需要在组合框中显示服务器端数据时,我会创建一个临时本地表并导入请求的记录。这很耗时,特别是对于大桌子。

能够使用记录集来填充组合框控件将允许用户直接显示来自服务器端的数据。

受前面两个例子的启发,我写了一些代码如下:

Dim rsPersonne as ADODB.recordset
Set rsPersonne = New ADODB.Recordset

Set rsPersonne.ActiveConnection = connexionActive
rsPersonne.CursorType = adOpenDynamic
rsPersonne.LockType = adLockPessimistic
rsPersonne.CursorLocation = adUseClient

rsPersonne.Open "SELECT id_Personne, nomPersonne FROM Tbl_Personne"

fc().Controls("id_Personne").Recordset = rsPersonne

在哪里:

  • connexionActive:是我到数据库服务器的永久 ADO 连接
  • fc(): 是我当前/活动的形式
  • 控件(“id_Personne”):是用于填充公司员工列表的组合框控件
  • 2003年访问版本

不幸的是,它不起作用!

在调试模式下,我能够检查记录集是否已正确创建,包含请求的列和数据,并与组合框控件正确关联。不幸的是,当我显示表单时,我不断得到一个空的组合框,里面没有任何记录!非常感谢任何帮助。

编辑:

这个记录集属性确实适用于特定的组合框对象,而不适用于标准控件对象,几天前我很惊讶地发现了它。我已经尝试过使用组合框的回调函数,或者使用组合框的“addItem”方法填充列表。所有这些都非常耗时。

4

6 回答 6

5

如前所述,您必须将 RowSourceType 设置为“Table/List”(如果是法语,则为“Table/Requête”)才能在组合框中显示查询结果。

您的内存问题来自于打开记录集 (rsPersonne) 而不关闭它。您应该在关闭/卸载表单时关闭它们(但是由于记录集是在函数中而不是在表单中声明的​​,所以您会再次遇到范围问题)。

您还可以尝试使用 Access 的内置查询创建器创建和保存查询,并将相同的查询插入组合框的 RowSource。这样,查询在 Access 中得到验证和编译。

于 2009-07-14T17:24:32.920 回答
5

要将接受行源的控件设置为记录集,请执行以下操作:

Set recordset = currentDb.OpenRecordset("SELECT * FROM TABLE", dbOpenSnapshot)
Set control.recordset = recordset

可以肯定地使用 DAO 记录集,我没有尝试过 ADO 记录集,因为我没有任何真正的理由使用它们。

这样做后,简单的重新查询将无法刷新数据,您必须重复 set 语句。

于 2013-02-01T03:55:18.757 回答
3

我找到了诀窍......组合框控件的“rowSourceType”属性必须设置为“表/列表”。显示现在没问题,但我现在有另一个内存问题。由于我在表单上使用这些 ADO 记录集,每次浏览表单时,Access 的内存使用量都会增加。停止浏览或关闭表单都不会释放内存,从而使 MS Access 不稳定并经常冻结。如果我不能解决这个问题,我会提出一个问题

于 2009-06-09T10:23:38.283 回答
2

使用 Recordset 属性的好方法,感谢您的提示!

Patrick,您在页面上显示的方法有一个很大的缺点(我自己也尝试过):值列表只能是 32 KB,如果超过此限制,函数将抛出错误。回调方法有一个很大的缺点,它非常慢,并且每个条目都会调用一次,这使得它无法用于更长的列表。使用记录集方法效果很好。我需要这个,因为我的 SQL 字符串超过 32 KB(WHERE ID IN(x,x,x,x,x...) 的很多索引值)。

这是一个简单的函数,它使用这个想法为组合框设置一个记录集:

' Fills a combobox with the result of a recordset.
'
' Works with any length of recordset results (up to 10000 in ADP)
' Useful if strSQL is longer than 32767 characters
'
' Author: Christian Coppes
' Date: 16.09.2009
'
Public Sub fnADOComboboxSetRS(cmb As ComboBox, strSQL As String)
    Dim rs As ADODB.Recordset
    Dim lngCount As Long

   On Error GoTo fnADOComboboxSetRS_Error

    Set rs = fnADOSelectCommon(strSQL, adLockReadOnly, adOpenForwardOnly)

    If Not rs Is Nothing Then
        If Not (rs.EOF And rs.BOF) Then
            Set cmb.Recordset = rs
            ' enforces the combobox to load completely
            lngCount = cmb.ListCount
        End If
    End If

fnADOComboboxSetRS_Exit:
    If Not rs Is Nothing Then
        If rs.State = adStateOpen Then rs.Close
        Set rs = Nothing
    End If
    Exit Sub

fnADOComboboxSetRS_Error:
    Select Case Err
        Case Else
            fnErr "modODBC->fnADOComboboxSetRS", True
            Resume fnADOComboboxSetRS_Exit
    End Select
End Sub

(函数 fnADOSelectCommon 打开一个 ADO 记录集并将其返回。函数 fnErr 显示一个带有错误的消息框,如果有的话。)

由于此函数关闭打开的记录集,因此内存应该没有问题。我对其进行了测试,并没有看到在使用组合框关闭表单后没有释放的内存增加。

在表单的卸载事件中,您还可以使用“Set rs=Me.Comboboxname.Recordset”,然后将其关闭。这对于内存来说不是必需的,但最好释放打开的连接(如果与后端数据库服务器一起使用)。

干杯,

基督教

于 2009-09-16T15:54:33.563 回答
0

组合框控件没有记录集属性。它确实有一个 RowSource 属性,但 Access 需要一个 SQL 字符串。

您可以将 RowSourceType 更改为用户定义的“回调”函数的名称。通过将自己定位在 RowSourceType 上并按 F1,访问帮助将为您提供更多信息,包括示例代码。当我想为用户提供可用报告、驱动器号或其他无法通过 SQL 查询获得的数据的列表时,我会使用这种类型的函数。

关于直接从服务器端使用数据,我不明白您的第三段是什么意思。或者更确切地说,我不明白使用标准查询有什么问题。

于 2009-06-09T03:01:01.003 回答
0

在 MS Access 中,没关系,但在 VB 中,您可以使用 adodc (Jet 4.0) 使用类似的东西:

Private sub Form1_Load()
   with Adodc1
     .commandtype = adcmdtext
     .recordsource = "Select * from courses"
     .refresh

     while not .recordset.eof
           combo1.additem = .recordset.coursecode
           .recordset.movenext
     wend
   end with
End Sub
于 2011-12-12T04:31:55.220 回答