IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Contribuez Discussion :

macro - negatif en positif et inversement


Sujet :

Contribuez

  1. #1
    Membre du Club
    Homme Profil pro
    Analyste d'exploitation
    Inscrit en
    Janvier 2013
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations professionnelles :
    Activité : Analyste d'exploitation
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2013
    Messages : 48
    Points : 45
    Points
    45
    Par défaut macro - negatif en positif et inversement
    Bonjour,

    Je post içi ma 1er contribution en espérant mon étude de cas n'a pas déjà été fait et qu'elle pourra servir à d'autre.

    Je cherchais comment rendre positif un nombre négatif et inversement.
    Après beaucoup de recherche infructueuse (je pensais trouver une solution toute faite), je me suis mis à créer ma propre procédure.
    Je tiens juste à signaler que je suis débutant et que j'ai énormément de lacune. Donc tous les conseils et remarques utiles sont les bien venu


    Maintenant que c'est dit passons au choses sérieuses :

    • Copier les cellules d'une colonne sur la colonne de droite
    • Inverser les valeurs négatif en positif et positif en négatif
    • Ne pas toucher aux valeurs d'origine
    • le faire à partir d'une cellule active


    A partir de la cellule active, la sélection se fait sur toutes les cellules pleines de la colonne et va donc s’arrêter dès qu'il rencontre une cellule vide.
    Il copie les valeur sur la colonne de droite (attention si il y a des données, elles seront écraser. Bien ajouter une colonne vide) et inverser les valeurs.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
     
    Sub inversValPosNeg()
    Dim var1
     
    Set a = Range(Selection, Selection.End(xlDown))
    Set b = Range(Selection, Selection.End(xlDown)).Offset(0, 1)
    b.Clear
    a.Select
    Message = "vous avez selectionné les cellules " & a.Address & " afin de les copier vers " & b.Address
    rep = MsgBox(Message, vbYesNo)
    If rep = vbNo Then GoTo quit
    a.Copy b
    Set Plage = b
            For Each cell In Plage
                var1 = (cell * -1)
                cell.Value = var1
            Next
    quit:
    End Sub
    Voilà. j'espère avoir été clair et précis.
    A vos com.

    Yannick

  2. #2
    Expert éminent sénior
    Avatar de Marc-L
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    9 468
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2013
    Messages : 9 468
    Points : 18 674
    Points
    18 674
    Par défaut
    Bonjour,

    les contributions ne sont pas - en général - d'un niveau débutant, elles sont censées répondre à un certain niveau de complexité,
    hormis parfois une astuce ou un raccourci, rien qu'en les consultant …
    Elles doivent apporter une certaine utilité, je dirais même plus une utilité certaine !

    En tant que débutant, mieux vaut présenter son code dans la section adéquate, Macros et VBA Excel, afin d'y obtenir aide & conseil.

    Ceci dit, voici mes critiques quant au code :
    • La variable var1 (explicite !) est définie en ligne n°3 mais pas les variables objet Range a, b & Plage


    • Ligne n°5 : et si la sélection comporte plusieurs cellules ? Dans l'énoncé il est pourtant question de la cellule active !


    • Ligne n°6 peut être raccourcie en partant de l'objet a, mais en fait on peut se passer de cette ligne !


    • Ligne n°7 inutile car la destination va être effacée par la copie et inversion de signe …


    • Ligne n°8 inutile.


    • Ligne n°9 : le message est à désirer car l'utilisateur n'a pas sélectionné de plage …


    • Ligne n°11 : Goto à proscrire, à remplacer par Exit Sub, donc ligne n°18 inutile.


    • Ligne n°12 inutile : pourquoi copier alors que les valeurs peuvent être calculées directement depuis la source !


    • Ligne n°13 inutile : la destination étant déjà définie, la dupliquer ne sert qu'à consommer de la mémoire !


    • Ligne n°15 : si la cellule source n'est pas une valeur numérique, cette ligne déclenche alors une erreur …


    • Ligne n°15 & 16 : la variable var1 est inutile car la cellule de destination peut être directement calculée depuis la cellule source,

    donc ligne n°3 plus utile !
    Voici un exemple du code optimisé :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    Sub CopieEtInverseSigne()
        Dim Cel As Range, Plage As Range
     
        Set Plage = Range(ActiveCell, ActiveCell.End(xlDown))
     
        If MsgBox("Copier les cellules " & Plage.Address(0, 0) & " vers " & _
            Plage.Offset(, 1).Address(0, 0) & " ?", vbYesNo, "Inverser signe") = vbNo Then Exit Sub
     
        Application.ScreenUpdating = False
     
        For Each Cel In Plage
            Cel.Offset(, 1).Value = -Cel.Value
        Next
     
        Application.ScreenUpdating = True
                         Set Plage = Nothing
    End Sub
    __________________________________________________________________________________________

    Merci de cliquer sur pour chaque message ayant aidé puis sur pour clore cette discussion …

  3. #3
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut heu
    Bonjour marc

    je rajouterais a tes commentaires
    un détail qui peut avoir son importance
    l'utilisation de (end(xldown) qui peut générer un arrêt du calcul des la première cellule vide (dommage)

    en même temps je suis assez d'accords avec toi quand au fait de copier pour modifier inutile a mon sens

    je suggère a rakhann974 de prendre compte de ces remarque comme des remarques constructives afin qu'il puisse nous délivrer un code digne de ce nom

    au plaisir

  4. #4
    Expert éminent sénior
    Avatar de Marc-L
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    9 468
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2013
    Messages : 9 468
    Points : 18 674
    Points
    18 674
    Par défaut

    Bonjour Patrick,

    exact et c'était pourtant dans ma liste comme la non vérification de plage vide …

  5. #5
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut re
    re
    bonjour marc et rakhann974

    il y a en vba des constantes et des variables pour faire cela

    en vba on justement la constante "sgn" qui
    determine le negatif ou le positif
    exemple

    machin =sgn(-100) donnera -1

    machin =sgn(100) donnera 1

    donc si l'on veut convertir la valeur d'une cellule en positif on fera comme ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    Dim cellule
    cellule = [a1]
    MsgBox cellule * (Sgn(cellule))
    voila voila
    a mediter

  6. #6
    Expert éminent sénior
    Avatar de Marc-L
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    9 468
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2013
    Messages : 9 468
    Points : 18 674
    Points
    18 674
    Par défaut

    Patrick, dans ce cas précis Sgn seul ne répond pas au besoin d'inverser un positif en négatif …

    Et de toute manière je ne vois pas mieux que l'opérateur ▬ ‼

    Pourquoi s'embêter avec une fonction alors que depuis la nuit des temps,
    bien avant le premier computer IBM de la taille d'un appart, bien avant le mathématicien Pascal,
    bien avant les Mathématiques, bref en simple arithmétique le signe ▬ inverse le signe …
    What else ?

    __________________________________________________________________________________________
    Les bourses ne témoignent pas l'état des économies, mais de la psychologie des investisseurs ! (Françoise Giroud)

  7. #7
    Membre du Club
    Homme Profil pro
    Analyste d'exploitation
    Inscrit en
    Janvier 2013
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations professionnelles :
    Activité : Analyste d'exploitation
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2013
    Messages : 48
    Points : 45
    Points
    45
    Par défaut
    Bonjour,

    Dire que j'étais fier de mon bout de code fait avec mes humbles connaissances.
    Je suis autodidacte dans ce domaine et j'espère vous pardonnerez mes maladresses.
    Finalement ne dit t-on pas qu'il y a 10 façons de programmer. La bonne et la mauvaise.
    Tout état de cause, je prend bonnes notes de toutes les remarques et conseils que vous m'avez apporter. le forum et l'entre aide est fait pour ça finalement.

    Merci encore

  8. #8
    Expert éminent sénior
    Avatar de Marc-L
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    9 468
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2013
    Messages : 9 468
    Points : 18 674
    Points
    18 674
    Par défaut


    Pour un débutant, tu peux être fier de ton code fonctionnant malgré tout !


    __________________________________________________________________________________________
    Le savoir est la seule matière qui s'accroit quand on la partage. (Socrate)

  9. #9
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut re
    re

    salut tout les deux

    marc je pense que tu te trompe sgn fait l'parfaitement affaire dans ce cas présent puisque dans l'énonce il dit "et vise et versa" sgn te donne automatiquement le signe de l'operateur

    Au plaisir

  10. #10
    Expert éminent sénior
    Avatar de Marc-L
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    9 468
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2013
    Messages : 9 468
    Points : 18 674
    Points
    18 674
    Par défaut

    Patrick, avec ton code du post #5 un positif reste un positif alors que la demande est d'inverser le signe …

    Donc pas la peine de chercher midi à 14 heures, l'opérateur ▬ (x = -x) suffit largement !

  11. #11
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut re
    Re bonjour rakhann974 et marc

    voila un code un peu epuré qui fait la meme chose
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
     
    Sub inversValPosNeg()
    Dim tablo As Variant
    tablo = Range(Selection, Selection.End(xlDown)).Value
    Selection.Offset(0, 1).Clear
     
    Message = "vous avez selectionné les cellules " & Selection.Address & " afin de les copier vers " & Selection.Offset(0, 1).Address
    rep = MsgBox(Message, vbYesNo)
     If rep = vbNo Then Exit Sub
     
            For i = 1 To UBound(tablo)
                    tablo(i, 1) = (tablo(i, 1) * -1)
            Next
     
    Selection.Offset(0, 1) = tablo
    End Sub
    on crée un tableau en mémoire avec tablo
    le principe est de boucler sur les items du tableau représentant la plage de cellule beaucoup plus rapide que boucler sur une plage

    dans la boucle inverser les valeur de chaques items du tableau

    retranscrire dans la selection.offset (0,1)tout simplement

    80% de temps d'exécution de gagné
    pas négligeable si longue plage

  12. #12
    Membre du Club
    Homme Profil pro
    Analyste d'exploitation
    Inscrit en
    Janvier 2013
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations professionnelles :
    Activité : Analyste d'exploitation
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2013
    Messages : 48
    Points : 45
    Points
    45
    Par défaut
    Salut patricktoulon,

    Désolé pour le retour tardif. Plein de taf en ce moment.

    J'ai testé ton code qui marche très bien mais qui nous oblige à selectionner les cellule à traiter avant.

    sur quelques-une ça va, mais sur des milliers c'est un peu galère.
    Sauf si on passe par le raccourci clavier pour effectuer la sélection. (ctrl + shift + bas)

    Il reste juste à adapter pour qu'il effectue la selection automatiquement avant.

    En tout état de cause, on se rend bien compte qu'il n'y a pas qu'une seule méthode. Même si, celle qui fourni un résultat le plus rapidement sera la meilleur, je pense.

  13. #13
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut
    Bonjour

    rakhann974;7547320]Salut patricktoulon,

    Désolé pour le retour tardif. Plein de taf en ce moment.

    J'ai testé ton code qui marche très bien mais qui nous oblige à selectionner les cellule à traiter avant.
    j'avoue ne pas comprendre ta remarque

    j'ai en fonction de ta demande et l'exemple que tu a donné au départ

    maintenant si tu veux faire avec une plage

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    Sub inversValPosNeg()
    Dim tablo As Variant,maplage as range
    set maplage=Range("a2:a1000")
    tablo = maplage.Value
    maplage.Offset(0, 1).Clear
     
    Message = "vous avez selectionné les cellules " & maplage.Address & " afin de les copier vers " & maplage.Offset(0, 1).Address
    rep = MsgBox(Message, vbYesNo)
     If rep = vbNo Then Exit Sub
     
            For i = 1 To UBound(tablo)
                    tablo(i, 1) = (tablo(i, 1) * -1)
            Next
     
    maplage.Offset(0, 1) = tablo
    End Sub
    voila voila
    Au plaisir

  14. #14
    Membre du Club
    Homme Profil pro
    Analyste d'exploitation
    Inscrit en
    Janvier 2013
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations professionnelles :
    Activité : Analyste d'exploitation
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2013
    Messages : 48
    Points : 45
    Points
    45
    Par défaut
    Bonjour patricktoulon,

    Je ne l'avais pas mis dans ma liste mais j'en ai parlé juste après :

    A partir de la cellule active, la sélection se fait sur toutes les cellules pleines de la colonne et va donc s’arrêter dès qu'il rencontre une cellule vide.
    Dans ce cas le code de Marc-L est plus adapté.

    Le problème que je pourrai rencontrer et qui ferait planter le travail, serait qu'il y ait autre chose qu'un nombre dans une cellule. Je devrais pouvoir le régler en mettant un contrôle.

    Encore une fois merci

  15. #15
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut re
    Bonjour
    pour la colonne entiere utilise plutôt le "xlup.end" tu est sur d'aller jusque qu a la derniere utilisée

    pour le test de la valeur(numeric ou ps
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if isnumeric(c.value) then
    tre simple comme concept

  16. #16
    Inactif  

    Homme Profil pro
    cuisiniste
    Inscrit en
    Avril 2009
    Messages
    15 374
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : cuisiniste
    Secteur : Bâtiment

    Informations forums :
    Inscription : Avril 2009
    Messages : 15 374
    Points : 12 068
    Points
    12 068
    Billets dans le blog
    8
    Par défaut re
    Bonjour
    mille excuses pour le retour tardif mais j'ai eu pas mal de boulot


    donc si je comprend bien tu sélectionne une cellule ou une plage dans lune colonne et tu veux inverser de la première cellule sélectionnée a la dernière cellules utilisée dans la colonne

    donc dans ce cas se sera:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
     
    Sub inversValPosNeg()
    Dim tablo As Variant, plage As Range
    Set plage = Range(Selection, Cells(Rows.Count, Selection.Column).End(xlUp))
    tablo = plage.Value
    plage.Offset(0, 1).Clear
    Message = "vous avez selectionné les cellules " & plage.Address & " afin de les copier vers " & plage.Offset(0, 1).Address
    rep = MsgBox(Message, vbYesNo)
     If rep = vbNo Then Exit Sub
     
            For i = 1 To UBound(tablo)
                    If tablo(i, 1) <> "" Then tablo(i, 1) = (tablo(i, 1) * -1)
            Next
     
    plage.Offset(0, 1) = tablo
    End Sub
    et en plus ca gère les cellules vides
    la vie est belle non????

    Au plaisir

  17. #17
    Membre du Club
    Homme Profil pro
    Analyste d'exploitation
    Inscrit en
    Janvier 2013
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations professionnelles :
    Activité : Analyste d'exploitation
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2013
    Messages : 48
    Points : 45
    Points
    45
    Par défaut
    Héhé !!! Tip Top

    C'est exactement ça.

    Merci MONSIEUR

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [RegEx] Regex sur entier negatif et positif
    Par User.Anonymous dans le forum Langage
    Réponses: 2
    Dernier message: 23/10/2009, 10h26
  2. Convertir un byte negatif en int positif
    Par Ghunter59 dans le forum Langage
    Réponses: 2
    Dernier message: 02/04/2009, 17h55
  3. Probleme inversion jour et mois lors d'une copie par macro
    Par alex830001 dans le forum Macros et VBA Excel
    Réponses: 4
    Dernier message: 11/09/2008, 15h29
  4. mettre un negatif en positif
    Par Guizmo95 dans le forum Linux
    Réponses: 4
    Dernier message: 25/09/2007, 09h19
  5. Réponses: 2
    Dernier message: 08/01/2007, 16h04

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo