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

Macros et VBA Excel Discussion :

[VBA Excel]Nombre hexa trop grand ?


Sujet :

Macros et VBA Excel

  1. #1
    Membre Expert Avatar de rtg57
    Homme Profil pro
    Autodidacte
    Inscrit en
    Mars 2006
    Messages
    1 343
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 59
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Autodidacte
    Secteur : Service public

    Informations forums :
    Inscription : Mars 2006
    Messages : 1 343
    Par défaut [VBA Excel]Nombre hexa trop grand ?
    Bonjour,

    j'effectue une opération logique XOR entre un nombre valant &H01FFFFFF et d'autres nombres:

    Pour &H01FFFFFF XOR un nombre inférieur à &H8000, tout va bien.

    Pour &H01FFFFFF XOR un nombre supérieur à &H8000, j'obtiens des résultats négatifs.

    Je pense que cela est dû à une limitation de capacité de bits.
    Même en faisant:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    &H01FFFFFF xor CLng(&H8000)
    cela ne fonctionne pas. Pourtantque CLng représente un nombre sur 4 octets.

    J'ai même essayé du :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    CDbl(&H01FFFFFF) xor CDbl(&H8000)
    ou du :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Cdbl( CDbl(&H01FFFFFF) xor CDbl(&H8000) )
    ...sans succès

    C'est quoi l'astuce ?

  2. #2
    pgz
    pgz est déconnecté
    Expert confirmé Avatar de pgz
    Homme Profil pro
    Développeur Office VBA
    Inscrit en
    Août 2005
    Messages
    3 692
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 72
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Office VBA
    Secteur : Conseil

    Informations forums :
    Inscription : Août 2005
    Messages : 3 692
    Par défaut
    Bonjour.

    Comme tu l'as dit, les entiers long sont codés sur 4 octets. Donc une opération comme &H01FFFFFF xor &H80000000 est tout à fait possible.

    Mais si tu ranges le résultat dans un entier court (2 octets)...

    Par exemple
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    Sub essai()
    Dim i As Integer
     
    ActiveSheet.Range("A1") = (&H1FFFFFF Xor &H1000000)
    i = &H8001
    ActiveSheet.Range("A2") = i
    End Sub
    vadonner pour résultat 16777215 et -32767. Pourquoi -32767? parce que pour un entier les nombres supérieurs à &H8000 sont les nombres négatifs!

    PGZ

  3. #3
    Membre Expert Avatar de rtg57
    Homme Profil pro
    Autodidacte
    Inscrit en
    Mars 2006
    Messages
    1 343
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 59
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Autodidacte
    Secteur : Service public

    Informations forums :
    Inscription : Mars 2006
    Messages : 1 343
    Par défaut
    Merci pour ces réponses,

    Pgz, mon post précise bien que j'ai fais les opérations avec des nombres de type Long (sur 4 octets) et type Double (sur 8 octets). Là où je n'ai pas été assez détaillé, c'est que je range ces résultats dans des variables de même longueur. Alors que dans votre exemple, vous travaillez avec un Integer sur 2 octets.

    Bref, j'en suis toujours au même point

    D'autres idées ?

  4. #4
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Bonjour, rtg57...

    j'ai pas la solution mais regarde, un petit jeu dans la fenêtre éxécution
    ? &h8000
    -32768
    ?&hFFFF8000
    -32768
    ?hex(-32768)
    FFFF8000
    ?hex(&h8000)
    8000
    (les valeurs en bleu sont les commande saisie , en noir le résultat)

    en séparant poids fort et poids faible on arrive à trouver le bon résultat :

    ?hex(&h01FFFFFF xor &h00008000)
    FE007FFF
    ?hex(&h01FF xor &h0000) & hex(&hFFFF xor &h8000)
    1FF7FFF

    j'ai pas trouvé la solution pour que &hFFFF8000 nous donne : 4294934528 et pas -32768 comme &h8000

  5. #5
    Membre Expert

    Profil pro
    Inscrit en
    Avril 2006
    Messages
    1 399
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2006
    Messages : 1 399
    Par défaut
    bonjour,

    A tester :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    Debug.Print &H1FFFFFF Xor &H8000&
    philippe

  6. #6
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Citation Envoyé par philben Voir le message
    bonjour,

    A tester :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    Debug.Print &H1FFFFFF Xor &H8000&
    philippe


    ?&H1FFFFFF Xor &H8000&
    33521663
    ?hex( &H1FFFFFF Xor &H8000&)
    1FF7FFF
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
       Dim yaLong As Long
       yaLong = Val("&H1FFFFFF&") Xor Val("&H8000&")
       MsgBox "Résultat : " & yaLong & " : " & Hex(yaLong)

  7. #7
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut j'avais laissé un _ (d'essai) au lieu de la variable montype ==>> corrigé
    Re,

    1) l'idée de philben mérite d'âtre saluée (Bravo à toi, philben)

    2) j'ai malgré tout voulu m'amuser à mettre en oeuvre la méthode que je suggérais un peu plus haut (en passant par des chaines binaires sur 32 bits)..
    Et j'ai un petit problème qui me laisse une espèce d'arrière-goût gênant ...

    Le code qui suit est auto-explicite, ainsi que son exécution :

    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
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    Private Sub Command1_Click()
      c1 = enbinaire(&H1FFFFFF, 32)
      c2 = enbinaire(&H8000, 32)
      MsgBox "voici mes 2 chaines en binaire " & vbCrLf & c1 & vbCrLf & c2
      For i = 1 To 32
        If Val(Mid(c1, i, 1)) <> Val(Mid(c2, i, 1)) Then chsortie = chsortie & "1" Else chsortie = chsortie & "0"
      Next
      MsgBox "voici ma chaîne de sortie" & vbCrLf & chsortie
      MsgBox " et voici le résultat en décimal de ma chaine de sortie avec montype = 8" & vbCrLf & _
       endecimal(chsortie, 8) & vbCrLf & vbCrLf & _
       "et voici le résultat en décimal de ma chaine de sortie avec montype = 32" & vbCrLf & endecimal(chsortie, 32)
    End Sub
     
     
    Private Function endecimal(ByVal Chaine As String, montype As Integer) As Integer
      Dim i As Integer
      For i = 1 To montype
        If Mid(Chaine, i, 1) = "1" Then endecimal = endecimal + (2 ^ (montype - i))
      Next
    End Function
     
    Private Function enbinaire(ByVal nombre As Currency, nbbits As Integer) As String
      Dim binaire As String, z As Currency, x As Currency
      binaire = ""
      z = 0
      x = 0
      Do Until nombre < 1
        x = nombre - (Int(nombre / 2) * 2)
        nombre = Fix(nombre / 2)
        binaire = CStr(x) + binaire
      Loop
      If nbbits > Len(binaire) Then
        binaire = String(nbbits - Len(binaire), Chr(48)) + binaire
      End If
      enbinaire = binaire
    End Function
    Ma gêne est la suivante : doit-on examiner la valeur de sortie sur 8 bits (et j'ai alors le même résultat que philben) ou sur 32 (et j'ai alors un résultat différent)... ?

  8. #8
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Citation Envoyé par ucfoutu Voir le message
    ...
    Ma gêne est la suivante : doit-on examiner la valeur de sortie sur 8 bits (et j'ai alors le même résultat que philben) ou sur 32 (et j'ai alors un résultat différent)... ?
    de quels 8 bits tu parle ?
    1FF7FFF
    du "FF" de droite

    et c'est quoi ton résultat ..?

    Il est logique que le résultat soit sur 32 bits, 4 octets...

  9. #9
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut
    Citation Envoyé par JackOuYA Voir le message
    et c'est quoi ton résultat ..?

    Il est logique que le résultat soit sur 32 bits, 4 octets...
    .
    Je crois (je l'ai dit) que mon code est suffisamment autoexplicite, non ?
    Et il affiche deux résultats différents selon que l'on reste ou non sur ces fameux 32 bits ...
    Quelqu'un d'autre aurait une explication complète ?

  10. #10
    pgz
    pgz est déconnecté
    Expert confirmé Avatar de pgz
    Homme Profil pro
    Développeur Office VBA
    Inscrit en
    Août 2005
    Messages
    3 692
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 72
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Office VBA
    Secteur : Conseil

    Informations forums :
    Inscription : Août 2005
    Messages : 3 692
    Par défaut
    Citation Envoyé par rtg57 Voir le message
    Merci pour ces réponses,

    Pgz, mon post précise bien que j'ai fais les opérations avec des nombres de type Long (sur 4 octets) et type Double (sur 8 octets). Là où je n'ai pas été assez détaillé, c'est que je range ces résultats dans des variables de même longueur. Alors que dans votre exemple, vous travaillez avec un Integer sur 2 octets.

    Bref, j'en suis toujours au même point

    D'autres idées ?
    Pourtant, &H1FFFFFF Xor &HFFFFFF donne 16777216 et pas un nombre négatif.

    A ce stade, et si tu ne veux pas en rester à ce point, il serait bien que tu montres le code qui pose problème puisque &H1FFFFFF Xor &HFFFFFF n'en pose pas. Pour info, sur 4 octets les nombres négatifs commencent à &H80000000. ET sur 2 octets à &H8000.

    PGZ

  11. #11
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Citation Envoyé par ucfoutu Voir le message
    Je crois (je l'ai dit) que mon code est suffisamment autoexplicite, non ?...
    j'ai pas regardé (marre de lire du HS) ... le seul truc c'est que je vois pas comment tu veut écrire :

    1FF7FFF
    avec 8 bits seulement...!

    tous tes 8 bits à 1 donne : FF ...

    montre donc ton résultat.... où dit nous où est ta méprise...?

  12. #12
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut
    Je crois, Jackouya, que tu devrais un peu t'écarter ...

    Le code que j'ai fait compare bien, caractère par caractère (donc bit à bit), deux chaines binaires de 32 bits...
    Si je parcours ces deux chaînes dans leur intégralité, mon résultat n'est pas 1 mais 2 ...
    Je souhaiterais vraiment que quelqu'un de plus averti me dise les choses de manière plus intelligible que "j'en ai marre du HS" !!!

  13. #13
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Citation Envoyé par ucfoutu Voir le message
    Je crois, Jackouya, que tu devrais un peu t'écarter ...

    Le code que j'ai fait compare bien, caractère par caractère (donc bit à bit), deux chaines binaires de 32 bits...
    Si je parcours ces deux chaînes dans leur intégralité, mon résultat n'est pas 1 mais 2 ...
    Je souhaiterais vraiment que quelqu'un de plus averti me dise les choses de manière plus intelligible que "j'en ai marre du HS" !!!
    ben le probléme n'est pas de comparer 2 chaines de caractére mais d'effectuer le XOR de 2 nombres de 32 bits... mon code donné plus haut donne le bon résultat :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     Dim yaLong As Long
       yaLong = Val("&H1FFFFFF&") Xor Val("&H8000&")
       MsgBox "Résultat : " & yaLong & " : " & Hex(yaLong)
    cela donne :

    Résultat : 33521663 : 1FF7FFF
    je te demande juste ce que donne tes 2 résultats en 8bits et 32 bits ..

  14. #14
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut
    Bon...

    Calmement, donc ...

    Le Xor compare, bit à bit, deux chaines binaires.
    C'est ce que je fais, en transposant en chaines binaires de 32 caractères (pour traiter des longs)
    Le résultat est une nouvelle chaîne binaire de 32 caractères. Cette chaîne est obtenue par concaténation (dit plus haut) d'un 0 ou d'un 1 à chaque comparaison de bit (c'est exactement le principe de Xor).
    Le résultat est une chaine binaire de 32 bits qui, traduite en décimal, me donne 2 et non le résultat de 1 trouvé par philben.
    Il suffit maintenant de lancer mon code pour y voir suffisamment clair sur ce que je dit.
    Pour info, maintenant : je viens de lancer mon code avec d'autres chiffres traités sans problèmes par le Xor. Dans ces cas-là (chiffres sans problèmes) Xor et mon code obtiennent le même résultat.
    Mon code n'est jamais rien d'autre que ce que fait Xor ... tu comprends ?

  15. #15
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    décidément je ne comprends rien à ce que tu écrit, philben n'as donné aucun résultat ni 1 ni 2 ?
    Citation Envoyé par philben
    bonjour,

    A tester :
    Code :

    Debug.Print &H1FFFFFF Xor &H8000&

    philippe
    merci pour le cours mais je sais ce qu'est un XOR appliqué sur 2 nombres de 32 bits..

  16. #16
    pgz
    pgz est déconnecté
    Expert confirmé Avatar de pgz
    Homme Profil pro
    Développeur Office VBA
    Inscrit en
    Août 2005
    Messages
    3 692
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 72
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Office VBA
    Secteur : Conseil

    Informations forums :
    Inscription : Août 2005
    Messages : 3 692
    Par défaut
    @ ucfoutu.

    As-tu remarqué que ta chaîne c2 donne, traduite en hexa : 00000000?
    Par contre si tu écris
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
      c2 = enbinaire(&H8000&, 32)
    tu obtiens alors 00008000. Normal, voir post de Philben pour forcer un long, au lieu d'UN ENTIER COURT.

    ENsuite je pense que tu as un problème ici
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
        If Mid(Chaine, i, 1) = "1" Then endecimal = endecimal + (2 ^ (8 - i))
    Il ne te paraît pas bizarre ce 8? MAis si tu mets montype, tu cours au dépassement de capa avec 32...

    Cordialement,

    PGZ

  17. #17
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut
    Oui, pgz. Merci ...

    Le 8 (laissé là à la suite d'essais successifs ) est à remplacer par la variable montype (j'ai corrigé mon code plus haut)

  18. #18
    Membre Expert

    Profil pro
    Inscrit en
    Avril 2006
    Messages
    1 399
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2006
    Messages : 1 399
    Par défaut
    bonjour à tous,

    j'en suis arrivé à la même conclusion que pgz mais en retard...

    Si la fonction d'ucfoutu retourne un long, on retombe sur nos pieds a priori :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    Private Function endecimal(ByVal Chaine As String, montype As Integer) As Long
      Dim i As Integer
      For i = 1 To montype
        If Mid(Chaine, i, 1) = "1" Then endecimal = endecimal + (2 ^ (montype - i))
      Next
    End Function
    Amicalement,

    Philippe

  19. #19
    Inactif  

    Profil pro
    Inscrit en
    Juillet 2007
    Messages
    4 555
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2007
    Messages : 4 555
    Par défaut
    Voilà, en effet ....
    Sinon on a un overflow sur les grands nombres...
    Nous y sommes maintenant tout-à-fait ... et tout-à-fait d'accord ...

    Je reste assez content d'avoir fait un autre Xor (voilà qui aura eu le mérite de le "décortiquer")
    Merci.

  20. #20
    Membre Expert
    Avatar de JackOuYA
    Inscrit en
    Juin 2008
    Messages
    1 040
    Détails du profil
    Informations forums :
    Inscription : Juin 2008
    Messages : 1 040
    Par défaut
    Citation Envoyé par ucfoutu Voir le message
    Voilà, en effet ....
    Sinon on a un overflow sur les grands nombres...
    Nous y sommes maintenant tout-à-fait ... et tout-à-fait d'accord ...

    Je reste assez content d'avoir fait un autre Xor (voilà qui aura eu le mérite de le "décortiquer")
    Merci.

    j'ai compris pourquoi tu ne voulais pas me répondre à la question simple ... quel est le retour de ta fonction .?..


    bon avec le type long c'est mieux.

    sauf que faudra me dire l'intérêt de ton XOR
    qui ne fais rien de plus que

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    Dim yaLong As Long
       yaLong = &H1FFFFFF& Xor &H8000&

+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 2 12 DernièreDernière

Discussions similaires

  1. VBA Excel: Nombre de fichiers Excel ouverts
    Par mamid1706 dans le forum Macros et VBA Excel
    Réponses: 7
    Dernier message: 18/01/2008, 15h26
  2. [VBA-Excel] - nombre de cas possibles
    Par Chewi dans le forum Macros et VBA Excel
    Réponses: 4
    Dernier message: 30/01/2007, 10h53
  3. [VBA-Excel] Nombre total de ligne d'un onglet
    Par marsupilami34 dans le forum Macros et VBA Excel
    Réponses: 3
    Dernier message: 04/01/2007, 23h38
  4. [vba-excel] Le temps de fermeture trop court ?
    Par Damsou dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 11/01/2005, 10h03

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