VBA, fichier des lignes avec une meme cellule

Résolu/Fermé
amdbg Messages postés 17 Date d'inscription lundi 27 juillet 2009 Statut Membre Dernière intervention 22 juin 2011 - 21 juin 2011 à 18:38
eriiic Messages postés 24603 Date d'inscription mardi 11 septembre 2007 Statut Contributeur Dernière intervention 15 décembre 2024 - 22 juin 2011 à 15:27
Bonjour,

Je souhaite créer une macro applicable à différentes plages de données de même type mais de longueurs différentes.

Dans la première colonne, j'ai le code produit. J'aimerais avoir un fichier (ou une feuille) par produit, qui porte le nom du produit.

Dans la première ligne de mon fichier d'origine, j'ai le nom des colonnes que je souhaite conserver dans chaque fichier.

Je souhaite donc que ma macro cherche dans la colonne A tous les codes qui sont les mêmes et créée un fichier (ou une feuille) comprenant toutes les lignes avec un même code pour chacun des codes.

J'espère que mon explication est claire. N'hésitez pas à me demander des précisions!




Je planche dessus depuis un bout de temps mais j'ai vraiment du mal. J'ai essayé de créer non pas des fichiers mais des feuilles. Ce code ne fonctionne pas et ne met pas la première ligne de mon fichier.



Sub creer_feuille()

A = Cells(2, 1)

Sheets.Add.Name = A


End Sub

'Je suis obligée de faire 2 sub car la feuille nouvellement créer devient active


Sub Trier_sur_feuilles()

A = Cells(2, 1)


    If B = Columns(1).Find(What:=A, After:=Cells(1, 1), LookIn:=xlValues, SearchOrder:=xlByRows, SearchDirection:=xlNext, MatchCase:=False, SearchFormat:=False).Activate is True Then Rows.Copy (Sheets("A"))


End Sub




Je vous serais vivement reconnaissante de votre aide. Je débute avec VBA et même si il y a énormément d'information sur internet, j'ai vraiment des difficultés avec ce langage!




A voir également:

3 réponses

Bonjour,

Voici un début :-)

Option Explicit 

Sub Creer_Feuille() 

    Dim A As String 
    Dim Fle_Origine As String 
     
    ' Capture de la feuille active 
    Fle_Origine = ActiveSheet.Name 
     
    ' Capture de la valeur recherché 
    A = Cells(2, 1).Value 

    ' Si valeur différent de rien 
    If (A <> "") Then 
        ' Ajout d'une feuille au nom désiré 
        Sheets.Add.Name = A 
    End If 
     
    ' Retour à la feuille de départ 
    Sheets(Fle_Origine).Select 
     
    ' Ce bout ci n'est pas clair pour moi 
    ' veuillez détailler s.v.p. 
    ' Quel est la valeur de B, d'où vient cette variable ?
    If (B = Columns(1).Find(What:=A, _ 
                           After:=Cells(1, 1), _ 
                           LookIn:=xlValues, _ 
                           SearchOrder:=xlByRows, _ 
                           SearchDirection:=xlNext, _ 
                           MatchCase:=False, _ 
                           SearchFormat:=False).Activate Is True) Then 
                            
        Rows.Copy (Sheets(A)) 
         
    End If 

End Sub 
' 


Cdt

Lupin
0
eriiic Messages postés 24603 Date d'inscription mardi 11 septembre 2007 Statut Contributeur Dernière intervention 15 décembre 2024 7 247
Modifié par eriiic le 22/06/2011 à 12:11
Bonjour,

Autre proposition (si j'ai bien compris la demande...) :
Sub creerFeuilles()
    Dim nbcol As Long, lig As Long, derlig As Long, nomF As String, nlig As Long
    Dim sh1 As Worksheet, sh2 As Worksheet
    Application.ScreenUpdating = False
    Set sh1 = Worksheets("donnees")
    nbcol = [A1].End(xlToRight).Column
    derlig = [A65536].End(xlUp).Row
    For lig = 2 To derlig
        nomF = sh1.Cells(lig, 1)
        ' création de la feuille si besoin
        If Not existSh(nomF) Then
            Sheets.Add.Name = nomF
            ActiveSheet.Move After:=Worksheets(Worksheets.Count)
            sh1.Cells(1, 1).Resize(1, nbcol).Copy ActiveSheet.[A1]
        End If
        ' copie donnée
        nlig = 1
        While sh1.Cells(lig + nlig, 1) = sh1.Cells(lig, 1)
            nlig = nlig + 1
        Wend
        sh1.Cells(lig, 1).Resize(nlig, nbcol).Copy Worksheets(nomF).[A65536].End(xlUp).Offset(1, 0)
        lig = lig + nlig - 1
    Next lig
    Application.ScreenUpdating = True
    sh1.Activate
End Sub

Function existSh(nom As String) As Boolean
    ' test l'existence d'une feuille
    Dim b As Boolean
    On Error GoTo suite
    Sheets(nom).Activate
    b = True
suite:
    existSh = b
End Function


Au début je met nbcol (nombre de colonnes copiées) égal au nombre de colonnes remplies consécutives de la ligne 1. Tu peux remplacer par la valeur que tu veux.

http://www.cijoint.fr/cjlink.php?file=cj201106/cijIHGHqGw.xls

eric

PS: cette macro agit sur la feuille active. Tu devrais ajouter un test au début pour reconnaitre la feuille et ne faire le traitement que si la feuille est concernée.
0
amdbg Messages postés 17 Date d'inscription lundi 27 juillet 2009 Statut Membre Dernière intervention 22 juin 2011
Modifié par amdbg le 22/06/2011 à 10:34
Bonjour!

Merci beaucoup de m'avoir répondu aussi vite!

Lupin, tu as raison, il n'y a pas vraiment d'intérêt à définir B. Je souhaite juste rechercher les lignes dont la première cellule est la même et les sélectionner.

Eric, ta macro fonctionne très bien sur ton exemple mais elle nécessite un débogage dans mon fichier, l'erreur affichée est "Indice en dehors de la plage (erreur 9)"; au niveau de la ligne

Set sh2 = Worksheets(sh1.Cells(lig, 1).Value)


J'ai rajouté 2 lignes de code pour être sûre que la feuille avec les données était sélectionnée, mais l'erreur apparaît toujours.

Option Explicit

Sub creerFeuilles()

ActiveSheet.Name = "donnees"

    Dim nbcol As Long, lig As Long, derlig As Long ', ok As Boolean
    Dim sh1 As Worksheet, sh2 As Worksheet
    Set sh1 = ActiveSheet
    nbcol = [A1].End(xlToRight).Column
    derlig = [A65536].End(xlUp).Row
    For lig = 2 To derlig
        ' création de la feuille si besoin
        If Not existSh(sh1.Cells(lig, 1)) Then
            Sheets.Add.Name = sh1.Cells(lig, 1)
            ActiveSheet.Move After:=Worksheets(Worksheets.Count)
            sh1.Cells(1, 1).Resize(1, nbcol).Copy ActiveSheet.[A1]
        End If
        ' copie donnée
        
        Sheets("donnees").Activate
        
        Set sh2 = Worksheets(sh1.Cells(lig, 1).Value)
        sh1.Cells(lig, 1).Resize(1, nbcol).Copy sh2.[A65536].End(xlUp).Offset(1, 0)
    Next lig
End Sub

Function existSh(nom As String) As Boolean
    ' test l'existence d'une feuille
    Dim b As Boolean
    On Error GoTo suite
    Sheets(nom).Activate
    b = True
suite:
    existSh = b
End Function
0
eriiic Messages postés 24603 Date d'inscription mardi 11 septembre 2007 Statut Contributeur Dernière intervention 15 décembre 2024 7 247
Modifié par eriiic le 22/06/2011 à 10:48
Bonjour,

Une feuille n'a pas été crée peut-être à cause d'un caractère interdit (?)
Difficile de te répondre sans la colonne A de la feuille qui bugue (celle sur laquelle tu appliques la macro).
Déposer le fichier sur cijoint.fr et coller ici le lien fourni.
S'il reste des données confidentielles dessus tu peux me le déposer en mp (cliquer sur mon nom pour accéder à mon profil et 'Lui écrire un message'.
Le .activate ajouté ne sert à rien...
eric
0
eriiic Messages postés 24603 Date d'inscription mardi 11 septembre 2007 Statut Contributeur Dernière intervention 15 décembre 2024 7 247
22 juin 2011 à 12:19
Re,

J'ai adapté le code a ton fichier, c'était dû au fait que les noms étaient des nombres au départ.

J'ai aussi modifié la copie des données. Tu n'avais pas dit qu'il y avait 5000 lignes...
Le traitement de ton fichier est passé de 2 min à 5 s. Si la colonne A est triée tu auras la vitesse maxi.
J'ai mis à jour le code et le fichier joint du post 3.

Une question me vient : si la feuille est existante les données sont ajoutées, au risque de doubler toutes les données en cas de mauvaise manip.
Ne serait-il pas préférable de détruire la feuille pour partir sur une feuille vierge ?
Tout dépend si tu auras besoin de cumuler des traitements.

eric
0
amdbg Messages postés 17 Date d'inscription lundi 27 juillet 2009 Statut Membre Dernière intervention 22 juin 2011
22 juin 2011 à 15:10
Oui je n'ai pas préciser la longueur du fichier, et encore, celui ci fait parti des plus cours!

Je ne vois pas ce que tu veux dire, au risque de doubler les données?

J'aurais en effet besoin de cumuler les traitements, par exemple, après avoir créer des feuilles de données par rapport au code produit, je voudrais pouvoir procéder de la même façon pour le serie_id ou le prod_lib

Yes ça marche sur mon fichier! C'est vraiment super merci.
0
eriiic Messages postés 24603 Date d'inscription mardi 11 septembre 2007 Statut Contributeur Dernière intervention 15 décembre 2024 7 247
22 juin 2011 à 15:27
J'aurais en effet besoin de cumuler les traitements, par exemple, après avoir créer des feuilles de données par rapport au code produit, je voudrais pouvoir procéder de la même façon pour le serie_id ou le prod_lib
Ce n'est pas tout à fait ce que je voulais savoir.
Si tu relances la macro une 2nde fois, une feuille crée de 4 données se retrouvera avec 2x4 données.
Faut-il supprimer toutes les feuilles nécessaire avant de faire le traitement pour éviter ça ?
Bien sûr si tu as 2 feuilles de datas à cumuler sur une feuille crée ce n'est pas faisable.

Par ailleurs on peut ajouter un choix de la colonne à prendre en nom de feuille avant de lancer le traitement (attention qu'il n'y ai pas de doublon de nom possible d'une colonne sur l'autre...)

eric
0