24

我正在使用下面的代码来获取 VBA 中过滤数据行的计数,但是在获取计数时,它给出了运行时错误显示:

“所需对象”。

有人可以让我知道需要什么更改吗?

Set rnData = .UsedRange

With rnData
    .AutoFilter Field:=327, Criteria1:=Mid(provarr(q), 1, 2)
    .Select
    .AutoFilter Field:=328, Criteria1:=Mid(provarr(q), 3, 7)
    .Select
    .AutoFilter Field:=330, Criteria1:=Mid(provarr(q), 10, 2)
    .Select
    .AutoFilter Field:=331, Criteria1:=Mid(provarr(q), 12, 2)
    .Select

     Rowz = .AutoFilter.Range.SpecialCells(xlCellTypeVisible).Rows.count

     ....
End With
4

8 回答 8

65

如果您尝试像这样计算已经自动过滤的范围内的行数:

Rowz = rnData.SpecialCells(xlCellTypeVisible).Rows.Count

它只会计算自动过滤范围的第一个连续可见区域中的行数。例如,如果自动过滤范围是第 1 到 10 行,并且第 3、5、6、7 和 9 行被过滤,则有四行可见(第 2、4、8 和 10 行),但它会返回 2,因为第一个连续可见范围是第 1 行(标题行)和第 2 行。

更准确的替代方法是(假设ws包含带有过滤数据的工作表):

Rowz = ws.AutoFilter.Range.Columns(1).SpecialCells(xlCellTypeVisible).Cells.Count - 1

我们必须减去 1 才能删除标题行。我们需要在我们的计数范围中包含标题行,因为如果没有找到任何单元格,SpecialCells 会抛出错误,这是我们想要避免的。

Cells即使 Range 有多个区域,该属性也会为您提供准确的计数,这与该Rows属性不同。所以我们只取自动过滤范围的第一列并计算可见单元格的数量。

于 2013-06-25T01:03:28.350 回答
26

只需将其放入您的代码中:

Application.WorksheetFunction.Subtotal(3, Range("A2:A500000"))

确保应用正确的范围,但只保留一列

于 2016-04-15T08:15:43.657 回答
3

虽然我同意给出的结果,但它们对我不起作用。如果您的表有一个名称,这将起作用:

Public Sub GetCountOfResults(WorkSheetName As String, TableName As String)
    Dim rnData As Range
    Dim rngArea As Range
    Dim lCount As Long
        Set rnData = ThisWorkbook.Worksheets(WorkSheetName).ListObjects(TableName).Range
    With rnData
        For Each rngArea In .SpecialCells(xlCellTypeVisible).Areas
            lCount = lCount + rngArea.Rows.Count
        Next
        MsgBox "Autofilter " & lCount - 1 & " records"
    End With
    Set rnData = Nothing
    lCount = Empty      
End Sub

这已修改为与我在此处找到的原始版本的 ListObjects 一起使用:

http://www.ozgrid.com/forum/showthread.php?t=81858

于 2016-01-09T02:26:06.060 回答
2

我知道这是一个旧线程,但我发现在 VBA 中使用 Subtotal 方法也可以准确地呈现行数。我找到的公式在这篇文章中,看起来像这样:

Application.WorksheetFunction.Subtotal(2, .Range("A2:A" & .Rows(.Rows.Count).End(xlUp).Row))

我对其进行了测试,每次都准确地显示出来,在 A 列中呈现正确数量的可见行。

希望这将帮助像我这样的“网络”的其他旅行者。

于 2015-10-05T21:24:55.317 回答
1

我找到了一种方法,它需要 2 个步骤,但它有效

' to copy out a filtered selection into a different sheet


number_of_dinosaurs = WorksheetFunction.Count(Worksheets("Dinosaurs").Range("A2", "A3000"))

With Worksheets("Dinosaurs")
    .AutoFilterMode = False
    With .Range("$A$4:$E$" & number_of_dinosaurs)
        .AutoFilter Field:=2, Criteria1:="*teeth*" ' change your criteria to whatever you like
        .SpecialCells(xlCellTypeVisible).Copy Destination:=Worksheets("Bad_Dinosaurs").Range("A1")
    End With
End With


' then do a normal count on the secondary sheet  

number_of_dinosaurs_that_eat_humans = WorksheetFunction.Count(Worksheets("Bad_Dinosaurs").Range("A2", "A30000"))
于 2017-07-27T13:34:43.253 回答
1
Rowz = Application.WorksheetFunction.Subtotal(2, Range("A2:A" & Rows(Rows.Count).End(xlUp).Row))
于 2020-07-03T00:33:56.967 回答
0

我认为现在您有了每一行的范围,您可以使用 offset(row, column) 操作轻松操作该范围?计算过滤的记录有什么意义(除非您需要在变量中计数)?因此,与其(或在同一个块中)编写代码操作以将每一行移动到一个空的隐藏工作表,一旦完成,您可以从传输的范围数据中做任何您喜欢的工作吗?

于 2015-02-11T02:14:56.023 回答
0
Rowz = Application.WorksheetFunction.Subtotal(2, Range("A2:A" & Rows(Rows.Count).End(xlUp).Row))

这对我很有效

于 2019-11-23T12:01:59.070 回答