web-dev-qa-db-fra.com

Nombre de lignes sur les données filtrées

J'utilise le code ci-dessous pour obtenir le nombre de lignes de données filtrées dans VBA. Toutefois, lorsque vous obtenez le nombre, il donne l'erreur suivante:

"Objet requis". 

Est-ce que certains pourraient me faire savoir quels changements sont nécessaires?

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
12
user2300403

Si vous essayez de compter le nombre de lignes de la plage déjà filtrée automatiquement, procédez comme suit:

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

Il ne comptera que le nombre de lignes de la première zone visible contiguë de la plage filtrée automatiquement. Par exemple. si la plage de filtrage automatique est les lignes 1 à 10 et les lignes 3, 5, 6, 7 et 9 sont filtrées, quatre lignes sont visibles (lignes 2, 4, 8 et 10), mais renverrait 2 car la première image contigu visible la plage correspond aux lignes 1 (la ligne d'en-tête) et 2.

Une alternative plus précise est la suivante (en supposant que ws contient la feuille de calcul avec les données filtrées):

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

Nous devons soustraire 1 pour supprimer la ligne d'en-tête. Nous devons inclure la ligne d'en-tête dans notre plage comptée, car SpecialCells émettra une erreur si aucune cellule n'est trouvée, ce que nous voulons éviter.

La propriété Cells vous donnera un décompte précis même si la plage comporte plusieurs zones, contrairement à la propriété Rows. Nous prenons donc simplement la première colonne de la plage de filtrage automatique et comptons le nombre de cellules visibles.

38
Jon Crowell

Il suffit de mettre ceci dans votre code:

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

Assurez-vous d’appliquer la plage correcte, mais conservez-la dans UNE colonne.

19
Frank

Bien que je sois d’accord avec les résultats donnés, ils n’ont pas fonctionné pour moi. Si votre table a un nom, cela fonctionnera:

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

Ceci est modifié pour fonctionner avec ListObjects à partir d'une version originale que j'ai trouvée ici:

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

2
Joe Stellato

J'ai trouvé un moyen de faire cela qui nécessite 2 étapes, mais cela fonctionne

' 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"))
1
warsong

Je sais que c'est un vieux fil de discussion, mais j'ai découvert que la méthode Subtotal dans VBA rend également le nombre de lignes avec précision. La formule que j'ai trouvée est dans cet article , et ressemble à ceci:

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

Je l'ai testé et il est sorti avec précision à chaque fois, rendant le nombre correct de lignes visibles dans la colonne A.

J'espère que cela aidera une autre personne du réseau comme moi.

1
Josh

Je penserais que maintenant vous avez la plage pour chaque ligne, vous pouvez facilement manipuler cette plage avec l'action offset (ligne, colonne)? Quel est l’intérêt de compter les enregistrements filtrés (sauf si vous en avez besoin dans une variable)? feuille cachée et une fois tout fait, vous pouvez faire le travail que vous aimez à partir des données de plage transférées?

0
Marc Quattrini