VBA。 300MB +优化macros

(在下面的代码之前/之后有更多的代码,这是我想优化循环的部分)

Sheets("LeanReport").Activate Dim lRow As Long On Error Resume Next lRow = Application.WorksheetFunction.Match("05 2016", Range("AB:AB"), 0) On Error GoTo 0 If lRow > 0 Then 'code End If For i = 2 To LastrowLeanReport R1 = CStr(Cells(i, 5)) RG1 = CStr(Cells(i, 24)) MatrizRG1(i - 2) = RG1 MatrizR1(i - 2) = R1 Next i Sheets("Carrier").Activate For i = 2 To LastrowCarrier RG2 = CStr(Cells(i, 1)) MatrizRG2(i - 2) = RG2 Next i For j = 2 To LastrowCarrier For p = lRow To LastrowLeanReport If MatrizRG2(j) = MatrizRG1(p) Then MatrizRG3(j) = Cells(j, 1) MatrizC1(j) = MatrizR1(p) End If Next p If MatrizRG3(j) = "" Then For x = 0 To lRow If MatrizRG2(j) = MatrizRG1(x) Then MatrizRG3(j) = Cells(j, 1) MatrizC1(j) = MatrizR1(p) End If Next x End If Next j 

有没有什么办法来优化这个macros? Lastrowleanreport有超过700000行我如何改变这些循环的东西?

它给我所有的时间错误6和7内存不足。

而不是将数据加载到matrix中,然后在matrix上运行,您可以直接在单元上运行。 那么你不消耗大matrix的内存。

为了达到这个目的,我首先改变了你的代码,这样我可以find等价的expression 例如,你将一些东西分配给一个matrix元素,然后使用这个元素。 那么这个用法就相当于从表单中获取数据并放入matrix元素中的expression式。

一旦完成,您可以将上次for循环中的matrix引用replace为单元格引用。 在这里,我看到一些有趣的东西:你的源工作表显然有2个标题行,你跳过。 但是之后在for循环中再次跳过它们,但是现在也跳过了前两个matrix元素! 我不认为这是你的意思:

 For j = 0 To LastrowCarrier - 2 For p = lRow To LastrowLeanReport If MatrizRG2(j + 2) = MatrizRG1(p) Then MatrizRG3(j + 2) = Cells(j + 2, 1) MatrizC1(j + 2) = MatrizR1(p) End If Next p If MatrizRG3(j + 2) = "" Then For x = 0 To lRow If MatrizRG2(j + 2) = MatrizRG1(x) Then MatrizRG3(j + 2) = Cells(j + 2, 1) MatrizC1(j + 2) = MatrizR1(p) End If Next x End If Next j 

在上面,我认为expression式j + 2应该只是j (除了在Cellsexpression式中)。 我继续在那里。 还要注意,在MatrizR1(p)是不明确的,因为它指向matrix之外(我把这个错误给你解决)。

接下来我介绍了工作表的variables,所以更容易处理它们。 我改变了循环从零开始到行计数 – 2.这给出了以下等效的子程序:

 Dim sheetCarrier As Worksheet Dim sheetReport As Worksheet Dim lRow As Long Set sheetReport = Sheets("LeanReport") sheetReport.Activate lRow = Application.WorksheetFunction.Match("05 2016", Range("AB:AB"), 0) For i = 0 To LastrowLeanReport - 2 MatrizRG1(i) = CStr(sheetReport.Cells(i + 2, 24)) MatrizR1(i) = CStr(sheetReport.Cells(i + 2, 5)) Next i Set sheetCarrier = Sheets("Carrier") For i = 0 To LastrowCarrier - 2 MatrizRG2(i) = CStr(sheetCarrier.Cells(i + 2, 1)) Next i For i = 0 To LastrowCarrier - 2 For p = lRow To LastrowLeanReport If MatrizRG2(i) = MatrizRG1(p) Then MatrizRG3(i) = sheetCarrier.Cells(i + 2, 1) MatrizC1(i) = MatrizR1(p) End If Next p If MatrizRG3(i) = "" Then For x = 0 To lRow If MatrizRG2(i) = MatrizRG1(x) Then MatrizRG3(i) = sheetCarrier.Cells(i + 2, 1) MatrizC1(i) = MatrizR1(p) End If Next x End If Next I 

在下一步中,我现在只需要将上一个循环中的matrix引用replace为早期循环中的单元引用。 这些等价物是:

 MatrizRG1(i) = CStr(sheetReport.Cells(i + 2, 24)) MatrizR1(i) = CStr(sheetReport.Cells(i + 2, 5)) MatrizRG2(i) = CStr(sheetCarrier.Cells(i + 2, 1)) 

(我不知道你在MatrizRG3MatrizC1中的输出在哪里,所以我把它放在代码中 – 对你来说是很好的练习。)

没有matrix的等价子程序就变成:

 Dim sheetCarrier As Worksheet Dim sheetReport As Worksheet Dim lRow As Long Set sheetCarrier = Sheets("Carrier") Set sheetReport = Sheets("LeanReport") sheetReport.Activate lRow = Application.WorksheetFunction.Match("05 2016", Range("AB:AB"), 0) For i = 0 To LastrowCarrier - 2 For p = lRow To LastrowLeanReport If CStr(sheetCarrier.Cells(i + 2, 1)) = CStr(sheetReport.Cells(p + 2, 5)) Then MatrizRG3(i) = sheetCarrier.Cells(i + 2, 1) MatrizC1(i) = CStr(sheetReport.Cells(p + 2, 5)) End If Next p If MatrizRG3(i) = "" Then For x = 0 To lRow If CStr(sheetCarrier.Cells(i + 2, 1)) = CStr(sheetReport.Cells(x + 2, 24)) Then MatrizRG3(i) = sheetCarrier.Cells(i + 2, 1) MatrizC1(i) = CStr(sheetReport.Cells(p + 2, 5)) ' note: this 'p' is undefined!! End If Next x End If Next i 

如果这样做(并检查它,错误很容易),那么我们可以继续看看是否可以优化一点。