🚀The world's best VBA AI has evolved. ExcelMaster is now an autonomous Agent.Read more →
Back to Blog

VBA Advanced Filter dans Excel — extraire des valeurs uniques et filtrer vers une nouvelle plage (sans boucle)

|

VBA Advanced Filter dans Excel — extraire des valeurs uniques et filtrer vers une nouvelle plage (sans boucle)

En brefRange.AdvancedFilter est le seul filtre qui vous remet des données, pas une vue. En un seul appel, il peut copier une liste unique ou un ensemble de lignes correspondant à des critères vers un autre emplacement, sans boucle et sans rien supprimer. Deux idées le déverrouillent. D'abord, Action choisit entre xlFilterInPlace (masque les lignes, comme AutoFilter) et xlFilterCopy (copie les résultats vers un CopyToRange — le mode puissant). Ensuite, sa « clause WHERE » n'est pas du code — c'est une plage de critères, un petit bloc de cellules dont l'en-tête doit correspondre exactement à celui de la source. Ajoutez Unique:=True et vous obtenez une liste distincte en une ligne, l'original restant intact.

' Extraire une liste distincte des valeurs Region de la colonne B vers la colonne E. Non destructif.
Dim ws As Worksheet: Set ws = ThisWorkbook.Worksheets("Sales")
ws.Range("B1:B1000").AdvancedFilter _
        Action:=xlFilterCopy, _
        CopyToRange:=ws.Range("E1"), _   ' E1 doit contenir le MEME en-tete que B1
        Unique:=True                     ' une occurrence de chaque valeur, source inchangee

AdvancedFilter est l'outil que l'on dégaine en dernier et que l'on devrait dégainer en premier. Quand il vous faut un résultat sous forme de données — une liste distincte, un export des lignes correspondant à une condition, une copie dédupliquée qui laisse l'original intact — l'instinct est d'écrire une boucle For Each avec un If et un Dictionary. Excel a déjà un moteur de requête fait exactement pour cela. Ce guide s'articule autour de ses deux idées fondatrices : il peut copier au lieu de masquer, et ses critères vivent dans des cellules.

Ce que vous allez apprendre

  • Le modèle mental — du SQL allégé pour une plage : extraire, pas seulement voir
  • Sur place ou copie — xlFilterInPlace face à xlFilterCopy
  • La plage de critères — votre clause WHERE vit dans des cellules, pas dans le code
  • Unique:=True — une liste distincte sans rien supprimer
  • Le piège de correspondance d'en-tête qui renvoie une sortie vide
  • AdvancedFilter vs AutoFilter vs RemoveDuplicates

Le modèle mental : du SQL allégé pour une plage

Voyez AdvancedFilter comme un minuscule moteur de requête greffé sur une plage. AutoFilter répond à la question « quelles lignes est-ce que je veux voir ? » et masque le reste sur place. AdvancedFilter répond à une question plus vaste : « donne-moi les lignes qui correspondent — sous forme d'un nouvel ensemble de données que je peux placer quelque part et exploiter. » Il peut lui aussi filtrer sur place, mais sa raison d'être est le mode copie : il prend une plage source, un ensemble facultatif de conditions, et écrit les lignes correspondantes (ou uniques) vers une destination de votre choix.

Ce recadrage compte, car il remplace toute une catégorie de boucles. « Obtenir les clients uniques », « sortir chaque commande supérieure à 1000 vers une feuille de rapport », « lister les codes produits distincts » — ce sont des extractions en un appel, pas des itérations. Gardez cette image en tête — AdvancedFilter produit des données, AutoFilter produit une vue — et vous saurez de laquelle une tâche a besoin.

Sur place ou copie : xlFilterInPlace vs xlFilterCopy

L'argument Action est le point de bifurcation :

  • xlFilterInPlace masque les lignes non correspondantes directement dans la plage source, exactement comme AutoFilter. Les données ne bougent pas ; vous obtenez une vue filtrée. Pour l'effacer ensuite, appelez ws.ShowAllData.
  • xlFilterCopy laisse la source tranquille et copie les lignes correspondantes vers CopyToRange. C'est le mode qui rend AdvancedFilter spécial — il est non destructif et produit un bloc de données distinct et exploitable.
' Mode copie - celui que vous voudrez le plus souvent.
ws.Range("A1").CurrentRegion.AdvancedFilter _
        Action:=xlFilterCopy, _
        CriteriaRange:=ws.Range("H1:H2"), _   ' la clause WHERE (voir plus bas)
        CopyToRange:=ws.Range("K1"), _        ' ou atterrissent les resultats
        Unique:=False

Si vous passez xlFilterCopy, vous devez fournir CopyToRange ; si vous passez xlFilterInPlace, vous ne le devez pas (Excel déclenche une erreur dans les deux sens si vous les mélangez). Dans le doute, copiez — cela ne touche jamais à votre original.

La plage de critères : votre clause WHERE vit dans des cellules

C'est la partie qui déroute quand on vient d'autres langages : AdvancedFilter ne prend pas une condition sous forme de chaîne ou d'expression. Ses conditions vivent dans une plage de critères — un petit bloc de cellules de la feuille. La ligne du haut contient des en-têtes de colonne qui correspondent à la source, et les lignes en dessous contiennent les conditions.

   H            I
1  Region       Amount
2  West         >1000

Cette plage de critères dit « Region vaut West ET Amount > 1000 ». Les conditions sur une même ligne sont un AND ; les conditions empilées sur des lignes distinctes sont un OR. Ainsi, deux lignes —

   H
1  Region
2  West
3  East

— signifie « Region vaut West OU East ». Vous pouvez construire ce bloc dans des cellules que votre macro possède (une zone de travail, ou une feuille masquée) et y pointer CriteriaRange :

ws.Range("A1").CurrentRegion.AdvancedFilter _
        Action:=xlFilterCopy, _
        CriteriaRange:=ws.Range("H1:I2"), _
        CopyToRange:=ws.Range("K1")

Omettez complètement CriteriaRange et aucune condition n'est appliquée — ce qui, combiné à Unique:=True, est exactement la façon d'obtenir une simple liste distincte.

Unique:=True — une liste distincte sans rien supprimer

Passez Unique:=True et AdvancedFilter renvoie une occurrence de chaque ligne distincte (ou valeur, pour une seule colonne) — le même résultat que Supprimer les doublons, sauf qu'il copie les valeurs uniques et laisse la source intacte. Cette seule propriété fait d'AdvancedFilter la façon sûre de dédupliquer :

' Noms de clients distincts vers la colonne K, liste d'origine intacte.
ws.Range("C1:C5000").AdvancedFilter _
        Action:=xlFilterCopy, _
        CopyToRange:=ws.Range("K1"), _
        Unique:=True

Là où RemoveDuplicates supprime sur place sans annulation, celui-ci vous remet une liste dédupliquée toute fraîche sans jamais risquer l'original. Quand quelqu'un demande « comment obtenir des valeurs uniques en VBA sans saccager les données », voici la réponse.

Le piège de correspondance d'en-tête qui renvoie une sortie vide

La raison numéro un pour laquelle AdvancedFilter « ne renvoie rien » est une non-correspondance d'en-tête. L'en-tête de la CriteriaRange comme celui du CopyToRange doivent correspondre aux en-têtes source exactement — même orthographe, mêmes espaces, même texte à la casse près. Un en-tête de critère « Reigon » (faute de frappe), ou un CopyToRange dont la cellule du haut est vide ou mal libellée, produit une sortie vide ou erronée sans déclencher d'erreur.

Deux habitudes l'évitent :

  • Construisez les en-têtes des critères et de la destination en copiant les vraies cellules d'en-tête, jamais en les retapant.
  • Si vous filtrez vers une autre feuille, rappelez-vous une vieille règle : l'AdvancedFilter classique veut le CopyToRange sur la feuille active. Le schéma robuste consiste à lancer le filtre depuis la feuille où atterrissent les résultats, ou à filtrer vers une plage de travail sur la feuille source puis à déplacer le résultat ensuite.

Quand la sortie revient vide, vérifiez les en-têtes avant toute autre chose.

AdvancedFilter vs AutoFilter vs RemoveDuplicates

Ils se recoupent assez pour semer la confusion et diffèrent assez pour que cela compte :

  • AutoFilter — une vue. Masque les lignes sur place pour que l'utilisateur voie un sous-ensemble ; rien n'est copié ni retiré. Recourez-y pour afficher une plage filtrée.
  • AdvancedFilter (mode copie) — une requête. Extrait les lignes correspondantes ou uniques vers un nouvel emplacement, de façon non destructive. Recourez-y quand il vous faut le résultat sous forme de données.
  • RemoveDuplicates — une suppression. Réduit les données sur place, garde la première de chaque, sans annulation. Recourez-y seulement quand vous voulez vraiment que la source elle-même soit plus petite et que vous avez une sauvegarde.

La phrase à retenir : AutoFilter affiche, RemoveDuplicates détruit, et AdvancedFilter est celui qui extrait — une liste distincte ou une copie filtrée par critères — sans toucher à l'original. Quand vous vous surprenez à écrire une boucle pour construire une liste filtrée ou unique, c'est le travail d'AdvancedFilter.

Comment ExcelMaster aide

AdvancedFilter est puissant précisément parce qu'il est délicat : la bifurcation sur place/copie, la plage de critères qui doit vivre dans des cellules avec des en-têtes qui correspondent à la lettre près, la destination de copie et sa règle de feuille active, l'option Unique. Trompez-vous sur un en-tête et il ne renvoie rien, en silence.

ExcelMaster vous laisse plutôt décrire la requête. Dites « sors chaque commande supérieure à 1000 de la région Ouest vers une nouvelle feuille » ou « donne-moi la liste distincte des codes produits », et il met en place la plage de critères avec des en-têtes copiés depuis la source, choisit le mode copie avec un CopyToRange valide, active Unique quand vous voulez des valeurs distinctes, et laisse les données d'origine intactes. Vous gardez le classeur et le code ; vous vous épargnez la demi-heure passée à vous demander pourquoi un en-tête de critère mal tapé a renvoyé un résultat vide.

Questions fréquentes

Comment utiliser Advanced Filter en VBA ?

Appelez AdvancedFilter sur la plage source : choisissez Action:=xlFilterCopy pour copier les résultats ailleurs (avec un CopyToRange) ou xlFilterInPlace pour masquer les lignes non correspondantes. Fournissez une CriteriaRange pour les conditions, ou passez Unique:=True sans critères pour extraire une liste distincte. En mode copie, les données source restent inchangées.

Comment extraire des valeurs uniques avec Advanced Filter en VBA ?

Utilisez le mode copie avec Unique:=True et sans critères : rng.AdvancedFilter Action:=xlFilterCopy, CopyToRange:=ws.Range("E1"), Unique:=True. Il écrit une occurrence de chaque valeur distincte vers la destination et laisse la source intacte — contrairement à RemoveDuplicates, qui supprime sur place. L'en-tête du CopyToRange doit correspondre à celui de la source.

Pourquoi Advanced Filter en VBA ne renvoie-t-il rien ?

Presque toujours une non-correspondance d'en-tête. Les en-têtes de la ligne du haut de CriteriaRange et de CopyToRange doivent correspondre exactement aux en-têtes source (une faute de frappe ou un en-tête vide renvoie une sortie vide sans erreur). Copiez les vraies cellules d'en-tête au lieu de les retaper, et assurez-vous qu'un filtre en mode copie a un CopyToRange valide.

Quelle est la différence entre AutoFilter et Advanced Filter en VBA ?

AutoFilter produit une vue — il masque les lignes non correspondantes sur place et ne copie rien. AdvancedFilter produit des données — en mode copie, il extrait les lignes correspondantes ou uniques vers un nouvel emplacement sans modifier la source, et il prend en charge des critères complexes AND/OR ainsi que l'extraction de valeurs uniques, ce dont AutoFilter est incapable.

Comment fonctionnent les critères dans Advanced Filter en VBA ?

Les critères vivent dans une plage de cellules, pas dans le code. La ligne du haut contient des en-têtes qui correspondent à la source ; les conditions sur une même ligne se combinent avec AND, et les conditions sur des lignes distinctes se combinent avec OR. Pointez CriteriaRange sur ce bloc. Omettez-le pour n'appliquer aucune condition (utile avec Unique:=True).

Testé dans

Testé dans : Excel 365 (Windows 11), VBA 7.1 — dernière vérification le 10/08/2026.

Guides associés : VBA AutoFilter · VBA Remove Duplicates · VBA Sort · VBA Find · VBA Range