【问题标题】:Excel VBA Dynamic Array spill only complete after end of macroExcel VBA 动态数组溢出仅在宏结束后完成
【发布时间】:2021-05-17 17:25:00
【问题描述】:

我的数据集包含 2020 年 3 月的几笔外币交易。 A 列包含每笔交易的日期,而 B 列包含外币 (EUR) 的交易价值。

我想使用 VBA 计算 C 列中以当地货币(即 ZAR)为单位的每笔交易的价值。

首先,我使用 STOCKHISTORY 函数获取 2020 年 3 月的所有汇率:

Dim exchangeRateSummary As Range

Range("I1").Formula2R1C1 = "=STOCKHISTORY(R1C5,R1C6,R1C7)"  'where R1C5 contains EUR/ZAR, R1C6 contains 01-Mar-20, and R1C7 contains 31-Mar-20
Set exchangeRateSummary = Range("I1").CurrentRegion  'save range as variable

然后我在 C 列中添加一个 VLookup 来确定每笔交易的当地货币价值,方法是遍历每一行:

Dim j As Integer

For j = 2 To 100
cells(j,3).value=cells(j,2).value * Application.WorksheetFunction.VLookup(Cells(j,1),exchangeRateSummary,2,False)
Next j

当我运行代码时,我收到以下错误:“无法获取 WorksheetFunction 类的 VLookup 属性。”当我按下 End 时,汇率的溢出范围(使用 stockhistory 函数创建)出现在我的 Excel 工作表上。当我再次运行代码时,VLookup 可以正常工作,并在 C 列中提供正确的本地货币值。

因此问题在于 VLookup 在同一个宏中不起作用,因为股票历史函数创建的溢出范围仅在宏执行后才会出现。

一种选择是让这些代码分开宏,但我想一键自动执行此过程。

有没有一种方法可以指示宏首先计算并溢出该范围,然后继续 VLookup 到该范围?

【问题讨论】:

  • 请编辑您的问题并将代码粘贴到讨论中。不然很难理解你的意思……
  • 这个问题可以使用更多细节,但我认为您遇到的是STOCKHISTORY 检索信息的延迟,而不是溢出数组的问题。
  • 从我所做的一些实验来看,问题似乎是STOCKHISTORY 的值保持#BUSY 直到所有VBA 代码完成运行。比我更有知识的人需要回答如何强制函数进行评估。我尝试了 DoEvents 和 20 秒的延迟。这些都不起作用。

标签: arrays excel vba dynamic vlookup


【解决方案1】:

您的问题不清楚,您应该尝试改进它。也就是说,根据您提供的内容,我认为您可以通过在您调用vlookup 的函数中强制计算来做一些事情。我的猜测是,简单地包装 vlookup 可能就足够了,而不必包含 Workshet.Calculate 调用,但除非您可以在问题中提供更多信息,否则您必须自己进行试验。

类似: 在您的工作表中,例如$A$1 中的股票字段,$A$2 中的开始日期从 B1 调用 STOCKHISTORY

in Cell B1
=STOCKHISTORY(A1, A2)

然后调用一个包含 vlookup 的函数,由 $B$1 中的更改触发,传递您的查找值(例如“2020 年 1 月 31 日”)。

=vlookup_wrapper("31-Jan-2020", B1)

你的包装看起来像这样

Option Explicit

Function vlookup_wrapper(ByVal lookup_val As Variant, ByVal spill_formula) As Variant
  'parameter spill_formula never used, only to trigger this function to be called
  Dim ws As Worksheet
  Set ws = ThisWorkbook.Sheets("sheet_with_stockhistory_formula")
  ' force stock history to finish its SPILL
  ws.Calculate

  'Define range from output of STOCKHISTORY spill
  Dim r_in As Range
  Set r_in = ws.Range(ws.Range("B1"), ws.Range("B1").End(xlDown))

  ' Assume want column 2 back
  vlookup_wrapper = Application.WorksheetFunction.VLookup(lookup_val, r_in, 2, False)
  
End Function

【讨论】:

    【解决方案2】:

    溢出范围参考来自#

    如果包含动态 STOCKHISTORY 公式的顶部单元格位于例如在H2。无法测试,但 VBA 应该可以完成这项工作。

    因此可能会收到一个可能发明的查找结果,例如通过

    Dim result: result = [VLOOKUP(100,H2#,2,FALSE)]
    

    result = Evaluate("VLookup(" & mySearch & "," & "H2#" & ",2,False")
    
    
     
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-09-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-05-30
      相关资源
      最近更新 更多