MS-Access 获取字段值,通过 VBA 函数运行,并发送到 SQL

Posted

技术标签:

【中文标题】MS-Access 获取字段值,通过 VBA 函数运行,并发送到 SQL【英文标题】:MS-Access Get field value, run through VBA function, and send to SQL 【发布时间】:2015-05-27 13:21:58 【问题描述】:

从 SQL SELECT 语句(例如 SELECT doubLat("SELECT [Map index].[Latitude] FROM [Map index]") AS decLat FROM...)调用函数时,如何单独返回每个项目的值?我希望这是通过方法(在 VBA 中)而不是 SQL 本身来完成的。

请注意,我不是指更改数据库本身中的任何字段值;目标只是将修改后的版本传递给 SQL 以进行进一步处理。我目前的方法如下所示。

Function doubLat(strSQL As String) As Double
    Dim db As Database
    Dim rs As DAO.Recordset
    Set db = CurrentDb

    If (strSQL <> "") Then
        Set rs = db.OpenRecordset(strSQL)
        For i = 0 To rs.Fields.Count - 1 'For each field in the recordset'
            If (rs.Fields(i).Name = "Latitude") Then
                doubLat = CDbl(LatToDecimal(rs.Fields(i).Value))
                MsgBox (doubLat) 'debug message'
            End If
        Next i
        rs.Close
    End If
End Function

LatToDecimal 采用 DMS 纬度值并以字符串形式返回 Decimal 纬度值。 doubLat(如上所示)用作将该 String 转换为 Double 以执行进一步操作的包装器。

如果目标是稍后在查询中的另一个函数中使用此数据,如何将从此类函数检索到的单个值传递回 SQL 查询并与生成它们的记录相关联(最好是暂时的)?

编辑:有关以下查询的更多信息。

SELECT...[Map index].[Map_Date], doubLat("SELECT [Map index].[Latitude] FROM [Map index]") AS decLat FROM [Map index]WHERE...AND (decLat BETWEEN 39 AND 41)

显示的最后一个条件 (decLat BETWEEN 39 AND 41) 最终将被替换为使用 hasrsine 函数和用户定义距离的条件。

我正在尝试做的一个例子是here,需要注意的是我需要稍后在查询中访问“新”数据(输出)。

当前的 doubLat 函数是here。 (编辑:由于缺少rs.MoveNext 导致的错误已得到纠正。)

最终结果:正如所料,解决方案相当简单。 SELECT语句需要调用doubLat([Map index].[Latitude]) AS decLat,其中doubLat如下图。

Function doubLat(ByVal latIn As String) As Double
    Dim newLat As Double
    newLat = CDbl(LatToDecimal(latIn))
    doubLat = newLat
End Function

请注意,此解决方案尚未正确考虑 [Map index].[Latitude] 中的空值,并将针对这些记录将 decLat 设置为 #Error

【问题讨论】:

使用唯一标识符?我无法清楚地理解您的问题。你能用简单的英语解释一下,不要用任何技术术语,也许用一些例子来解释你想要什么? 我有一个包含纬度字段的数据库。我想将该字段的内容用作查询的一部分,但需要先重新格式化。 (因为它在 DMS 中,我需要 Decimal 来实现另一个功能。) 只需将其包装在另一个选择中:进行选择查询,您可以在其中转换并执行所有需要的操作,但将条件 decLat BETWEEN 39 AND 41 排除在外。然后创建第二个选择,在其中选择 FROM 前一个选择,现在使用条件 decLat BETWEEN 39 AND 41。而不是SELECT stuff FROM ... WHERE ... AND declat... 做类似SELECT t.* FROM (SELECT stuff FROM ... WHERE ...) AS t WHERE declat... 【参考方案1】:

rs.fields("Lattitude").value 将为您提供该字段的内容 - 这就是您的意思吗?至于将它与特定记录相关联,我通常有一个类似的循环

set rs= ...
rs.movefirst
do while not rs.eof 
   ...
   Lattidue=rs.fields("Lattitude").value
   ...
   rs.movenext
   loop

这一次处理记录集中的一条记录,因此您可以将纬度关联到同一记录的任何其他字段

【讨论】:

这绝对是一种在 VBA 中检索字段内容的更有效方式,但我想我的问题表述不够清楚;如何稍后在查询中使用转换后的值(函数的输出)?我目前正在尝试 luk2302 的包装方法。 此外,我正在尝试从该函数中获取值并将其传递回查询,如here。 你能澄清一下这个问题吗?一旦你有了 Latitude,或者在你上面的代码中,doubLat,你想用它做什么?一旦您在变量中获得了值,您应该能够稍后在脚本中使用该变量。举个简单的例子,你可以用Msgbox("Latitude: " & Lattitude & "; converted: " & doubLat)来显示。 问题是我需要将每个值单独传回查询(SQL)本身;除了返回值之外,我没有尝试在 VBA 脚本中对它们做任何事情。您发布的代码似乎对此不起作用,因为任何打开查询(调用 doubLat)的尝试现在都会导致 Access 停止响应。我在问题中添加了一个指向当前 doubLat 完整代码的链接。 好的,我误解了 - 你有一个函数可以从 Lattitude 转换为你想在查询中使用的 DoubLat。我认为您需要从函数中获得单个输出,而不是多个记录(尽管我不确定)。因此,您需要在函数内部获取选择标准——可能作为另一个参数或作为 SQL 字符串的一部分。您的 WHERE 子句会为您从表中获取唯一记录吗?

以上是关于MS-Access 获取字段值,通过 VBA 函数运行,并发送到 SQL的主要内容,如果未能解决你的问题,请参考以下文章

VBA (Ms-Access) 从宏调用成员函数

通过模块 [VBA] 获取表单字段值

如何通过 MS-Access VBA 中的 TextBox.OnKeyUp 属性传递 KeyCode

从 VBA (MS-Access) 填写 PDF 表单

如何在 ms-access 中使用 ISNULL 函数

如何在 ms-access VBA 中检索表的 odbc 数据库名称