【问题标题】:How to multiply a range of values in Excel by a scalar variable using VBA?如何使用 VBA 将 Excel 中的一系列值乘以标量变量?
【发布时间】:2022-08-14 23:21:52
【问题描述】:

我已经实现了这个方法来将每个数组元素乘以一个变量中保存的数字。它非常慢。

是否有一种公认的“最快”方法将范围内的每个元素乘以一个常数?或者至少一个不那么慢?我必须这样做 10 次,这需要几分钟。

MultFactor = 10
For Each cell In Sheet1.Range(\"B3:B902\")
    cell.Value = cell.Value * MultFactor
Next cell

Multiply Entire Range By Value? 中引用的解决方案乘以一个常量(不是变量)。如果我使用此代码(将范围从 \"A1:B10\" 更改为 \"B3:B902\"),我会得到一个无意义的答案。

Dim rngData As Range
Set rngData = Sheet12.Range(\"B3:B902\")
rngData = Evaluate(rngData.Address & \"*2\")

我在 B3:B902 中的原始值对于前 100 个元素左右为零,然后增加一点,最后减少并再次出现零,但最终在我的范围内是一系列数字,破坏了我范围内的所有内容。它从 -224.5 开始,一直减少 0.5 到最后一个单元格。

-224.5
-224.0
-223.5
 etc.

即使这样有效,我将如何修改它以使用变量 MultFactor?

  • 无论您将使用哪种解决方案:您需要格外小心,不要多次运行代码。我的建议是改用新列(为此,您可以使用简单的公式而不是代码)

标签: excel vba


【解决方案1】:

这将快数百到数千倍。不同之处在于,所有的计算都是针对 VBA 数组而不是直接针对工作表单元格的,一一进行。更新数组后,它会一次性写回工作表。这将工作表交互减少到只有两个实例,读取和写入数组。减少 VBA 代码接触工作表端任何内容的实例数量对于执行速度至关重要。

Sub Mozdzen()

    Const FACTOR = 10
    Const SOURCE = "B3:B902"
    
    Dim i&, v
    v = Sheet1.Range(SOURCE)
    For i = 1 To UBound(v)
        v(i, 1) = v(i, 1) * FACTOR
    Next
    Sheet1.Range(SOURCE) = v
    
End Sub

基于上述思想,管理代码的更好方法是使用专用函数封装数组乘法:

Sub Mozdzen()    
    Const FACTOR = 10
    Const SOURCE = "B3:B902"
    
    With Sheet2.Range(SOURCE)
        .Value2 = ArrayMultiply(.Value2, FACTOR)
    End With        
End Sub

Function ArrayMultiply(a, multfactor#)
    Dim i&
    For i = 1 To UBound(a)
        a(i, 1) = a(i, 1) * multfactor
    Next
    ArrayMultiply = a
End Function

【讨论】:

  • 这至少快了 100 倍。 (< 1 秒 vs 150 秒)如果 multfactor 存储在变量中,我只需删除函数中的“#”,每个人都很高兴。
【解决方案2】:

你需要:

rngData = Sheet12.Evaluate(rngData.Address & "*2")

因为地址属性默认不包含工作表名称(因此您的公式是在活动工作表范围 B3:B902 的上下文中评估的)

那么它需要:

rngData = Sheet12.Evaluate(rngData.Address & "*" & MultFactor)

添加你的变量。

【讨论】:

    猜你喜欢
    • 2021-04-19
    • 1970-01-01
    • 2022-07-20
    • 2010-11-26
    • 1970-01-01
    • 2011-04-22
    • 1970-01-01
    • 2018-08-02
    相关资源
    最近更新 更多