ms-access - 将 Access.Application 对象传递给函数 : Dim, Set, Object 如何使其工作?

标签 ms-access vba pass-by-reference currying

我在 Stack Overflow 页面中发现了这个(修改过的)函数,并一直试图让它工作而不放弃传递的对象(如果我严格在第一个例程它会起作用)。

是的,我知道有很多方法可以得到相同的答案(主要来自堆栈上的其他帖子),但是这里有一个通用概念,即将对象传递给我想掌握的函数--请暂时忘记该函数检查表是否存在。

Function FCN_CheckTblsExist(theDatabase As Access.Application, _
tableName As String) As Boolean  

'access.Application.CurrentData.AllTables.Count
'etc is the 'workaround enabling disposal of 
'the "theDatabase" object variable

    ' Presume that table does not exist.
    FCN_CheckTblsExist = False

    ' Define iterator to query the object model.
    Dim iTable As Integer

    ' Loop through object catalogue and compare with search term.


    For iTable = 0 To theDatabase.CurrentData.AllTables.Count - 1
        If theDatabase.CurrentData.AllTables(iTable).Name = tableName Then
            FCN_CheckTblsExist = True
            Exit Function
        End If
    Next iTable


End Function


Function callFCN_CheckTblsExist(tableName As String)  
'this is an example of a curried function?--step down in dimensionality

Dim bo0 As String    
Dim A As Object
Set A = CreateObject("Access.Application")

bo0 = FCN_CheckTblsExist(A, tableName)

MsgBox tableName & " Exists is " & bo0

End Function

我不知道 (theDatabase As Access.Application, . ) 部分是否正确,这可能是问题的根源,而不是 Dim、Set、Object (New? ) 辅助程序中可能需要的体操。也许存在引用库问题(我正在运行 Access 2013)。

更新:我不确定以下内容是否足够强大,但这就是我在本文前面的意思,只是为了完整性而将其放在这里。顺便说一句,这不是一个拆分应用程序,所以也许这就是以下工作的原因。我很欣赏 HansUp 的帖子,关于这个主题还没有说得足够多。无论如何

Public Function FCN_CheckTblsExist(tableName As String) As Boolean   'Call this function once for every table

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
Dim appAccess As New Access.Application
Dim theDatabase As Access.Application

    ' Presume that table does not exist.
    FCN_CheckTblsExist = False

    ' Define iterator to query the object model.
    Dim iTable As Integer

    For iTable = 0 To Access.Application.CurrentData.AllTables.Count - 1
        If Access.Application.CurrentData.AllTables(iTable).Name = tableName Then
            FCN_CheckTblsExist = True
            Exit Function
        End If
    Next iTable

End Function

只是想补充一点,我在技术上发布的最后一个函数将被视为部分柯里化(Currying)或无柯里化(Currying),具体取决于调用“Access.Application.CurrentData.AllTables”对函数范围的限制程度。作为“theDatabase”的替代品,仅将 Access.Application.CurrentDb.Name 创建的特定字符串替换到原始函数中...(theDatabse,...这才是真正的完全柯里化(Currying)。

无论如何,将对象传递给函数和库及其方法是本次讨论的主要焦点。当我解决 DAO 问题时,我应该对可能发生的情况有更好的感觉,然后我将相应地发布并标记最佳解决方案。

最佳答案

问题实际上并不在于将 Access.Application 对象传递给其他函数。相反,您创建 Access.Application 并稍后检查表是否存在,而无需在该 Access session 中打开数据库。在这种情况下,theDatabase.CurrentData.AllTables.Count 应该触发错误 2467,“您输入的表达式引用了一个已关闭或不存在的对象。”

我修改了这两个过程并在 Access 2010 中对其进行了测试。编译和运行都没有错误,并产生了我认为您想要的结果。

Function FCN_CheckTblsExist(theDatabase As Access.Application, _
        tableName As String) As Boolean

    Dim tdf As DAO.TableDef
    Dim blnReturn As Boolean

    blnReturn = False
    For Each tdf In theDatabase.CurrentDb.TableDefs
        If tdf.Name = tableName Then
            blnReturn = True
            Exit For
        End If
    Next ' tdf
    FCN_CheckTblsExist = blnReturn
End Function

Function callFCN_CheckTblsExist(DbPath As String, tableName As String)
    Dim bo0 As Boolean
    Dim A As Object

    Set A = CreateObject("Access.Application")
    A.OpenCurrentDatabase DbPath
    bo0 = FCN_CheckTblsExist(A, tableName)
    MsgBox tableName & " Exists is " & bo0
    Debug.Print tableName & " Exists is " & bo0
    A.Quit
    Set A = Nothing
End Function

注意,在尝试打开 DbPath 数据库之前,我没有包含任何检查它是否存在的规定。因此,如果您给它一个不存在的数据库路径,您将会收到错误。

DAO 引用问题:

DAO 3.6 是旧 DAO 系列的最后一个。它仅支持较旧的MDB类型数据库。当 Access 2007 引入 ACCDB 数据库类型时,引入了新的 DAO 库(Access 数据库引擎对象库,有时称为ACEDAO)。除了支持 ACCDB 数据库之外,ACEDAO 还可以支持较旧的 MDB 类型。

设置引用时,不要尝试同时选择两者。

这是我的项目引用的屏幕截图:

VBE Project References

当我在“立即”窗口中检查我的项目引用时,请注意ACEDAO甚至被称为DAO。我还运行了 callFCN_CheckTblsExist 过程来演示它在没有 DAO 3.6 引用的情况下也能正常工作:

enter image description here

这一切都基于 Access 2010。您使用的是 Access 2013,因此您的 ACEDAO 版本号可能不同,但其他所有内容都应该相同。

关于ms-access - 将 Access.Application 对象传递给函数 : Dim, Set, Object 如何使其工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31395279/

相关文章:

excel - Outlook 错误 : user-defined type not defined referring to Excel workbook

c# - 在此 .net 示例中是否应通过引用传递参数?

sql - 将数据插入有关系的表中

excel - 将代码放入用户表单而不是模块中是否有缺点?

c# - 为什么 MS access odbc 在 C# 中返回数字而不返回字符串?

excel - 在 Excel VBA 中删除包含 "xxx"的单元格(的行)的优雅方法

ios - 如何在准备中的 viewController 之间通过引用传递快速数组(对于 segue :?

c# - 有没有办法在应用程序域中传递和使用引用类型/值类型的地址? (C#)

c# - 如何在字段包含 char ' 的 Access 中运行查询

ms-access - asp.net core 1.如何将目标运行时更改为x86