在 vba 宏中有比这个 foreach 循环更快的选项吗?

Sch*_*ing 2 excel each vba for-loop

我正在尝试创建一个宏来格式化我的库存表。我只需要显示最多 8 的值,然后显示超过 9 的任何值。我还需要摆脱任何 0 或负数。

我需要在 C、D、E 和 F 列上运行此循环 4 次,并且文件长约 15,000 行。该代码在我调试时有效,但如果它只是运行,它会使应用程序崩溃。我知道我不能循环那么多,但是还有其他方法可以做到吗?

Call SetStockLevels(range("C3:C" & lastRow))

Private Sub SetStockLevels(range As range)

    For Each c In range
        If c.Value < 1 Then
            c.ClearContents
        ElseIf c.Value > 8 Then
            c.Value = "9+"
        End If
    Next

End Sub
Run Code Online (Sandbox Code Playgroud)

我已经分别在宏的开头和结尾调用了这些函数。

Public Sub speedup()

    Application.ScreenUpdating = False
    Application.DisplayStatusBar = False
    Application.Calculation = xlCalculationManual
    Application.EnableEvents = False

End Sub

Public Sub normal()

    Application.ScreenUpdating = True
    Application.DisplayStatusBar = True
    Application.Calculation = xlCalculationAutomatic
    Application.EnableEvents = True

End Sub
Run Code Online (Sandbox Code Playgroud)

Ray*_* Wu 5

此方法将范围值存储在数组中并从中处理,这应该比逐个单元格循环要快得多。

如果您在 CF 列中的起始行和结束行相同,则可以传递整个范围并一起处理。

Option Explicit

Private Sub Test()
    Dim lastRow As Long
    lastRow = Sheet1.Range("C" & Sheet1.Rows.Count).End(xlUp).Row
    
    SetStockLevels Sheet1.Range("C3:F" & lastRow)
End Sub

Private Sub SetStockLevels(setRng As Range)

    Dim tempArr As Variant
    
    tempArr = setRng.Value
    
    Dim i As Long
    Dim j As Long
    For j = LBound(tempArr, 2) To UBound(tempArr, 2)
        For i = LBound(tempArr, 1) To UBound(tempArr, 1)
            Select Case tempArr(i, j)
                Case Is < 1: tempArr(i, j) = ""
                Case Is > 8: tempArr(i, j) = "9+"
            End Select
        Next i
    Next j
    
    setRng.Value = tempArr
End Sub
Run Code Online (Sandbox Code Playgroud)