在调用 .add() 之前添加项目的字典对象

rid*_*y_w 5 excel scripting vba dictionary

我正在使用MS Scripting Runtime 库中的字典对象来存储一系列数组并根据需要对数组单元执行操作。有一个 for 循环来完成创建所有这些条目的过程。我的问题是,在使用该.exists属性时,它True甚至在添加项目之前就返回了。

更仔细的调试表明在 for 循环开始时将键添加到字典中,即使没有.add使用任何命令并且直到循环结束才会使用。

我尝试了几种不同的配置,但这是一个失败的简单示例:

Dim dTotals As Dictionary
Set dTotals = New Dictionary

dTotals.CompareMode = BinaryCompare

For Each cell In rAppID
    If Not dTotals.Exists(cell) Then
    Set rAppIDCells = Find_Range(cell, rAppID)
    Set rAppIDValues = rAppIDCells.Offset(0, 6)
    dAppIDTotal = WorksheetFunction.Sum(rAppIDValues)
    dTotals.Add Key:=cell.Value, Item:=dAppIDTotal
    End If
Next cell
Run Code Online (Sandbox Code Playgroud)

每个单元格包含一个字符串/唯一 ID。在 If 语句中,代码返回 false,即使在第一次迭代时也是如此。

小智 6

当我有一个手表试图返回“丢失”的键的项目时,我在调试时遇到了这个问题。实际上,当我真正观察 [scriptingdictonaryObject].exists() 条件时,进一步受挫的调试也遇到了同样的问题;我建议因为手表的原因加上“缺失”的键。当我移除手表并创建一个临时工作表以在运行时将数组复制到其中时,不再添加不需要的键。


Vic*_*Vic 5

官方文档中?? 对于脚本运行时,它说“如果在尝试返回现有项目时未找到密钥,则会创建一个新密钥并将其对应的项目留空。”

...是的,当您在循环中调试时,它似乎在“.exists”函数被调用之前就突然出现了。一切都很好...

而不是尝试添加刚刚添加的项目,如下所示:

dTotals.Add Key:=cell.Value, Item:=dAppIDTotal
Run Code Online (Sandbox Code Playgroud)

...只需将当前位于您键上的空对象设置为新对象:

dTotals(cell.Value) = dAppIDTotal
Run Code Online (Sandbox Code Playgroud)

所以你的代码块变成:

If Not dTotals.Exists(cell) Then
    Set rAppIDCells = Find_Range(cell, rAppID)
    Set rAppIDValues = rAppIDCells.Offset(0, 6)
    dAppIDTotal = WorksheetFunction.Sum(rAppIDValues)
    dTotals(cell.Value) = dAppIDTotal
End If
Run Code Online (Sandbox Code Playgroud)

瞧。我倾向于在每次重新访问 VBA 时重新发现这个“功能”。如果由于添加不打算存储的新密钥而导致内存泄漏,您可能还会注意到它的影响。