- Thème : classes, Collection et Dictionary | Durée : 45 min | Niveau : avancé.
- Classeur de départ :
VBA18_catalogue.xlsm (feuilles Catalogue et Synthèse), avec les fichiers clsArticle.cls et clsArticles.cls dans le même dossier (à télécharger sur la page parente). - Contexte : le catalogue de Brévalis Industries compte douze articles. Vous importez la classe clsArticle, rangez ses objets dans une Collection, puis dans une classe collection typée, clsArticles, qui accepte For Each et l'écriture courte catalogue("PS-12"). Vous combinez enfin la collection et un Dictionary pour valoriser le stock par famille.
- Ouvrir le classeur, puis l'éditeur Visual Basic (Alt+F11) et le module
Module1. - Importer la classe clsArticle.
- Ranger des objets dans une Collection : macro
TesterCollection. - Importer la classe collection clsArticles.
- Charger le catalogue dans clsArticles : macro
ListerAlertes. - Cocher la référence Microsoft Scripting Runtime.
- Valoriser le stock par famille : macro
ValoriserParFamille. - Répondre au questionnaire de fin de lab (5 questions, 80 % pour valider).
Importer la classe clsArticle
- Dans l'éditeur Visual Basic : Fichier > Importer un fichier (Ctrl+M), puis choisissez
clsArticle.cls. Le module clsArticle rejoint le dossier Modules de classe. - Une classe se réutilise d'un classeur à l'autre : Fichier > Exporter un fichier la sauve en .cls, Fichier > Importer un fichier l'ajoute à un autre projet. clsArticle est la classe du lab VBA16, complétée d'un champ public Famille.
Ranger des objets dans une Collection
Sub TesterCollection()
Dim colArticles As Collection
Dim art As clsArticle
Dim ws As Worksheet
Dim ligne As Long
Set colArticles = New Collection
Set ws = Worksheets("Catalogue")
For ligne = 2 To ws.Cells(ws.Rows.Count, 1).End(xlUp).Row
Set art = New clsArticle
art.Ref = ws.Cells(ligne, 1).Value
art.Designation = ws.Cells(ligne, 2).Value
colArticles.Add art, art.Ref
Next ligne
Debug.Print colArticles.Count; "articles | 3e : "; colArticles(3).Ref; " | PS-20 : "; colArticles("PS-20").Designation
For Each art In colArticles
If art.Ref Like "CN-*" Then Debug.Print " "; art.Designation
Next art
End Sub
- Une Collection range des éléments de n'importe quel type, avec une clé facultative (ici la référence). On lit un élément par son indice (à partir de 1) ou par sa clé, et For Each parcourt les éléments. Mais rien n'empêche d'y ranger autre chose qu'un article : la Collection n'est pas typée.
- Résultat attendu :
- La fenêtre Exécution affiche 12 articles, PS-12 en 3e position et la désignation de PS-20
- Les deux carénages nautiques (CN-40 et CN-60) sont listés par For Each
Importer la classe collection clsArticles
- Dans l'éditeur Visual Basic : Fichier > Importer un fichier (Ctrl+M), puis choisissez
clsArticles.cls. Le module clsArticles rejoint le dossier Modules de classe. - clsArticles enveloppe une Collection privée et n'accepte que des clsArticle : Add crée l'article et refuse une référence en double, Exists teste une clé sans parcourir la collection, Item, Count et Remove complètent l'ensemble. Deux attributs, invisibles dans l'éditeur, font d'Item le membre par défaut et de NewEnum l'énumérateur qui autorise For Each. Ils ne se saisissent pas : ils sont lus à l'importation du fichier .cls.
- Après l'importation, ouvrez le code de clsArticles : les lignes Attribute du fichier n'y apparaissent pas.
- Résultat attendu :
- clsArticles a bien un membre par défaut (Item) et un énumérateur (NewEnum)
Charger le catalogue dans clsArticles
Function ChargerCatalogue() As clsArticles
Dim cat As clsArticles
Dim art As clsArticle
Dim ws As Worksheet
Dim ligne As Long
Set cat = New clsArticles
Set ws = Worksheets("Catalogue")
For ligne = 2 To ws.Cells(ws.Rows.Count, 1).End(xlUp).Row
Set art = cat.Add(ws.Cells(ligne, 1).Value)
art.Designation = ws.Cells(ligne, 2).Value
art.Famille = ws.Cells(ligne, 3).Value
art.Prix = ws.Cells(ligne, 4).Value
art.Stock = ws.Cells(ligne, 5).Value
art.Seuil = ws.Cells(ligne, 6).Value
Next ligne
Set ChargerCatalogue = cat
End Function
Sub ListerAlertes()
Dim cat As clsArticles
Dim art As clsArticle
Dim ws As Worksheet
Dim ligne As Long
Set cat = ChargerCatalogue()
Debug.Print cat.Count; "articles | PS-12 existe : "; cat.Exists("PS-12"); " | prix de PS-12 : "; cat("PS-12").Prix
Set ws = Worksheets("Synthèse")
ws.Range("A1:C20").ClearContents
ws.Range("A1").Value = "Article à commander"
ws.Range("B1").Value = "Stock"
ws.Range("C1").Value = "Seuil"
ligne = 2
For Each art In cat
If art.EstSousSeuil Then
ws.Cells(ligne, 1).Value = art.Ref
ws.Cells(ligne, 2).Value = art.Stock
ws.Cells(ligne, 3).Value = art.Seuil
ligne = ligne + 1
End If
Next art
End Sub
- cat.Add crée et renvoie l'article : on le complète aussitôt. cat("PS-12") équivaut à cat.Item("PS-12") grâce au membre par défaut, et For Each art In cat fonctionne grâce à NewEnum. Le code appelant ne voit plus la Collection : il manipule un catalogue.
- Résultat attendu :
- La fenêtre Exécution affiche 12 articles, PS-12 existe : Vrai et son prix 564
- La feuille Synthèse liste les 4 articles à commander avec leur stock et leur seuil
Cocher la référence Microsoft Scripting Runtime
- Dans l'éditeur Visual Basic : Outils > Références, cochez Microsoft Scripting Runtime, puis OK.
- La dernière macro regroupe les valeurs par famille dans un Dictionary, en liaison anticipée : la référence Microsoft Scripting Runtime doit être cochée dans ce classeur.
Valoriser le stock par famille
Sub ValoriserParFamille()
Dim cat As clsArticles
Dim art As clsArticle
Dim dFamilles As Scripting.Dictionary
Dim ws As Worksheet
Dim cle As Variant
Dim ligne As Long
Set cat = ChargerCatalogue()
Set dFamilles = New Scripting.Dictionary
For Each art In cat
dFamilles(art.Famille) = dFamilles(art.Famille) + art.Valeur
Next art
Set ws = Worksheets("Synthèse")
ws.Range("E1").Value = "Famille"
ws.Range("F1").Value = "Valeur du stock"
ligne = 2
For Each cle In dFamilles.Keys
ws.Cells(ligne, 5).Value = cle
ws.Cells(ligne, 6).Value = Round(dFamilles(cle), 2)
ligne = ligne + 1
Next cle
End Sub
- La classe collection fournit les objets, le Dictionary les regroupe : la clé est la famille, l'élément cumule art.Valeur. Chaque outil fait ce qu'il sait faire, et la macro reste courte et lisible.
- Résultat attendu :
- La feuille Synthèse donne la valeur du stock des 5 familles (colonnes E et F)