如何尽可能有效地(在性能方面)对范围执行重复的CountIf()
?
阵列范围
由于每次对电子表格的读/写都会导致VBA代码变慢,因此建议尽可能少地执行此操作。通常,如果有人反复读/写一个范围,他或她应首先将该范围保存到数组,对数组执行操作,然后在必要时进行最终读取或写入电子表格。
示例值和代码
如何在CountIf()
范围内使用A2:A11
执行以计算每个值的计数并将其写入D2:D7
?我希望下面的代码可以工作:
Sub M1ArrayCount()
Dim arrNumbers() As Variant
Dim Long1 As Long
Dim Loop1 As Long
arrNumbers() = ThisWorkbook.Sheets(1).Range("A2:A11").Value
With ThisWorkbook.Sheets(1)
For Loop1 = 1 To 6
.Cells(Loop1 + 1, 4).Value = Application.CountIf(arrNumbers(), Loop1)
Next Loop1
End With
End Sub
CountIf()不适用于数组
但是,由于Application.CountIf()
仅适用于范围而非数组,D2:D7
在运行上述代码后都会显示#VALUE!
错误。必须找到替代品。
答案 0 :(得分:2)
我们正在寻找的解决方案是:
Application.Count(Application.Match(SavedArray(), Array([lookup_value]), 0))
通常返回行号的函数如何与数组配对并计数以返回正确的答案?你怎么算行数?
力学解释
非常感谢@Jeeped,以及它的工作原理:
它是Match(lookup value, lookup array, 0)
的一个未记录的功能,如果您将一个数组作为查找值,它将Match()
您针对查找数组输入的数组中的每个值。因此,对于上面的示例,对于Loop = 1
,它将变为:
{match(A2, Array("1"), 0),match(A3, Array("1"), 0), ... match(A11, Array("1"), 0)}
然后,按@Jeeped:
每次匹配都会返回一个数字或错误。
Count()
函数计算数字,而不是错误。因此,您可以计算A1:A11
中的任何值是否与Loop1
匹配。
最终代码和值
Sub M1ArrayCount()
Dim arrNumbers() As Variant
Dim Long1 As Long
Dim Loop1 As Long
arrNumbers() = ThisWorkbook.Sheets(1).Range("A2:A11").Value
With ThisWorkbook.Sheets(1)
For Loop1 = 1 To 6
.Cells(Loop1 + 1, 4).Value = Application.Count(Application.Match(arrNumbers(), Array(Loop1), 0))
Next Loop1
End With
End Sub
<强>问题强>
示例:
myarray = array("First","Second","Second","Third","Fourth")
那么
countif(myarray,"second")
语法是什么? (结果 应该等于2个计数)<强>答案强>
另请尝试:
MsgBox Application.Count(Application.Match(myArray, Array("Second"), 0))
答案 1 :(得分:0)
Dim rowin as integer 'this is a counter for the row index
For rowin = 2 To Sheets("Sheet1").UsedRange.Rows.Count
Sheets("Sheet1").Range("D" & rowin).Value = WorksheetFunction.CountIf(Range("A:A"), Range("C" & rowin))
Next