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

C Discussion :

Masque de bits, additions binaires, je suis paumé ..


Sujet :

C

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut Masque de bits, additions binaires, je suis paumé ..
    Bonjours tout le monde,

    Comme vous pouvez le voir, je débute en C.

    Je veut comparer deux nombres binaire mais que un seul 1 par rapport à la première chaine :
    101 [ceQueJeCherche] 100 => renvois vrai
    101 [ceQueJeCherche] 101 => renvois vrai
    101 [ceQueJeCherche] 010 => renvois faux

    Quel est la manière la plus simple pour faire ce que je veut ?

    Merci.
    Pierre.

  2. #2
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    [Notation en binaire]
    101 & 100 => renvoie 100 --> vrai
    101 & 101 => renvoie 101 --> vrai
    101 & 010 => renvoie 000 --> faux

    Le & simple est le ET bit-à-bit.
    Le && double est le ET booléen.
    Ici, c'est le & simple que tu dois utiliser.

  3. #3
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut
    Et 111&001 renvoie vrai alors que c'est faux.

  4. #4
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    Ben si, c'est vrai : Le résultat est 001... (En supposant qu'on exprime toujours en binaire)

  5. #5
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut
    Ben si, c'est vrai : Le résultat est 001... (En supposant qu'on exprime toujours en binaire)
    Apparemment le test est:
    "si les nombres diffèrent de plus de 2 bits c'est faux".
    Or 111 et 001 diffèrent de 2 bits et 111&001 rend 1 donc vrai alors que le test devrait rendre faux.

  6. #6
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    Ah, OK...
    Dans ce cas, je connais un moyen arithmétiiquement correct, mais ça m'étonnerait que ce soit optimisé:
    Tu fais a^b et tu comptes les bits à 1 (tu peux même utiliser une table de 256 valeurs si tu veux de la vitesse)

  7. #7
    Expert éminent

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Points : 6 911
    Points
    6 911
    Par défaut
    Citation Envoyé par Pierre.g
    Bonjours tout le monde,

    Comme vous pouvez le voir, je débute en C.

    Je veut comparer deux nombres binaire mais que un seul 1 par rapport à la première chaine :
    101 [ceQueJeCherche] 100 => renvois vrai
    101 [ceQueJeCherche] 101 => renvois vrai
    101 [ceQueJeCherche] 010 => renvois faux

    Quel est la manière la plus simple pour faire ce que je veut ?

    Merci.
    Pierre.
    Si j'ai bien compris la question:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    unsigned tmp = n1 ^ n2;
    return (tmp != 0) && (tmp ^ ~-tmp) == 0;

  8. #8
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut
    Tu pourrais expliciter?

    Sinon:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    unsigned char c1=0x05;
    unsigned char c2=0x02;
    unsigned char c3=c1^c2;
    double log=log2(c3);
    int n=c3==0||((int)log==log);
    devrait convenir, avec "#include <math.h>"
    -c1^c2 filtre les différences;
    -si il n'y a aucune différence "c3==0" rend vrai;
    -si il y a une seule différence, "c3" est donc une puissance entière de 2, donc son log en base 2 est entier et donc "(int)log==log" renvoie vrai.

  9. #9
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    OK, merci pour toutes vos réponses.

    Alors, Médinoc, le code suivant me renvois "Vrai" alors que je voudrais qu'il me renvois "Faux" :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
        int variable=10000100,
            aTrouver=00010000;
     
        if (variable&aTrouver)
        {
            printf("Vrai\n");
        }
        else
        {
            printf("Faux\n");
        }
    Jean-Marc : que fais le symbole variable1 ^ variable2 ? >> edit : je viens de trouver, c'est le ou exclusif (ou XOR).
    Le bout de code que tu me propose renvois toujours faux, par exemple si je compare :
    10000100
    00000100

    Seriousme : tu veut que je réexplique mon problème ?
    Sinon, pour ton code, pareil que pour Jean-Marc, il renvois toujours faux

    Je regarde vos codes, mais c'est un poil ardu vu le cour que j'ai lu pour l'instant.

    Merci à tous.

    PS : apparament je crois que je me suis mal expliqué :
    Je veut donc comparer deux chiffres binaires, par exemple :
    001001001
    000001000
    => je veut qu'en comparant les deux chiffres d'au dessus, ça me renvois vrai, parce qu'on retrouve le 1 du deuxième chiffre à la même place dans le premier.
    En faite je veut seulement voir si le seul un du deuxième chiffre est retrouvable à la même place dans le chiffre du bas.

    Merci.

  10. #10
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    Pierre.g : Le code devrait envoyer faux, mais tes nombres sont exprimés en décimal (et en octel) : Il n'existe pas de moyen en C d'exprimer un nombre en binaire.
    Par contre, tu peux les noter en hexadécimal ou en octal:

    Et là, le résultat devrait être bon.

  11. #11
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Arf, merci Médinoc, mais là je crois que je dévis un peut trop du problème initiale.

    Si ça te dérange pas, regarde ici si ce que tu me dis est bien ce qu'il faut que je fasse : http://www.developpez.net/forums/sho...08#post1282908

    Si oui, j'approfondirais, mais si non, ça fais un peut hardu pour mon niveau si je dois commencer à mélanger le decimale, l'octale et le binaire ...

    Merci.

  12. #12
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    L'opérateur de décalage de bits "<<" ou ">>" devrait faire ton bonheur dans une boucle.

  13. #13
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    OK, merci.

    Ce décalage de bit, ça marche aussi en C tout court (pas C++) ?
    Peut tu me donner un petit exemple de syntaxe pour s'en servir ?

    Sinon, pourais-tu m'expliquer vite fais comment je peut me servir de ce décalage de bit pour résoudre mon problème ?

    Merci beaucoup.

  14. #14
    Expert éminent

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Points : 6 911
    Points
    6 911
    Par défaut
    [QUOTE=seriousme][quote]
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    unsigned tmp = (unsigned)n1 ^ (unsigned)n2;
    return tmp != 0 && (tmp & ~-tmp) == 0;
    Tu pourrais expliciter?
    Comme on travaille avec des unsigned, c'est du complément à deux pour l'opérateur -. Pour -tmp, en commencant par les bits de poids faible on a donc autant de 0 que dans tmp, un 1 et puis on inverse les bits de tmp.

    ~-tmp c'est donc, toujours en commencant par les bits de poids faible, autant de 1 qu'il n'y a de 0 au début de tmp, un 0 et puis les mêmes bits que dans tmp. Autrement dit, ~-tmp, c'est tmp avec son premier 1 mis à 0. On fait un & binaire entre les deux, on a donc de nouveau ~-tmp (j'ai dû être distrait), et s'il est non nul c'est que tmp avait au moins deux bits mis à 1. Ma proposition est donc maintenant:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    unsigned tmp = (unsigned)n1 ^ (unsigned)n2;
    return tmp != 0 && ~-tmp == 0;

  15. #15
    Membre régulier
    Profil pro
    Inscrit en
    Mai 2006
    Messages
    138
    Détails du profil
    Informations personnelles :
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations forums :
    Inscription : Mai 2006
    Messages : 138
    Points : 124
    Points
    124
    Par défaut
    Bonjour tout le monde ,

    Donc tu connais la valeur qui correspond aux lecteurs cachés (par exemple 0110 0011 en binaire soit 0x63 en Hexa).

    Tu voudrais savoir si le lecteur B et F sont cachés (soit 0010 0010 en binaire donc 0x22 en héxa)

    Donc tu compare 0x63 & 0x22 à 0x22 et non pas à vrai ou à faux .
    si le résultat de 0x63 & 0x22 est égal à 0x22 (donc 0010 0010 en binaire) c que le lecteur B et F sont cachés.

    Dites moi si ce raisonnement tient la route.

  16. #16
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Merci Jean-Marc, mais ça ne marche toujours pas, alors est-ce que c'est moi qui est passé à coté d'un truc ? je voudrais que le code suivant me renvois "Vrai", pour l'instant, il me renvoit "Faux" :
    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
    #include <stdio.h>
    #include <stdlib.h>
     
    int compare (int n1, int n2)
    {
        unsigned tmp = (unsigned)n1 ^ (unsigned)n2;
        return tmp != 0 && ~-tmp == 0;
    }
     
    int main()
    {
        int var1=0001000100,
            var2=0000000100;
     
        if (compare(var1, var2))
        {
            printf("Vrai");
        }
        else
        {
            printf("Faux");
        }
     
    	getch();
    	return 0;
    }
    Fveysseire, oui, c'est exactement ça à pars que je vais tester les lecteurs un par un avec une boucle pour que ça soit plus simple.

    A+, Pierre.

    Je pense que je vais faire comme Médinoc m'avais conseillé, de tout convertir en hexadécimale et utiliser le &, apparament ça marche, j'essai de faire ce que je veut et je vous tiens au courant.

  17. #17
    Membre régulier
    Profil pro
    Inscrit en
    Mai 2006
    Messages
    138
    Détails du profil
    Informations personnelles :
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations forums :
    Inscription : Mai 2006
    Messages : 138
    Points : 124
    Points
    124
    Par défaut
    Si tu veux les tester un par un :

    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
     
     
    char MASQUE = 0x01;
    char tab[8];
    for (i=0; i < 8; i++)
    {
       MASQUE = MASQUE << i;
       if ((VALEUR_LECTEUR & MASQUE) == MASQUE)
       {
           tab[i] = 1;
       }
       else
       {
           tab[i] = 0;
       }
    }
    Ce bout de code (que je n'ai pas testé) devrais te convenir. Il permet de récupérer un tableau contenant les indications que tu veux sur les lecteurs.

  18. #18
    Membre régulier
    Profil pro
    Inscrit en
    Mai 2006
    Messages
    138
    Détails du profil
    Informations personnelles :
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations forums :
    Inscription : Mai 2006
    Messages : 138
    Points : 124
    Points
    124
    Par défaut
    Oups j'avais oublié que tu voulais avoir vrai ou faux le code devient :

    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
     
     
    char MASQUE = 0x01;
    char tab[8] = {A, B, C, D, E, F, G, H};
    for (i=0; i < 8; i++)
    {
       MASQUE = MASQUE << i;
       if ((VALEUR_LECTEUR & MASQUE) == MASQUE)
       {
           printf("Le lecteur %C est caché : Vrai", tab[i]);
       }
       else
       {
          printf("Le lecteur %C est caché : Faux", tab[i]);
       }
    }
    Par contre je ne suis pas sûr de l'initialisation du tableau.

  19. #19
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Ah, merci à tous, on n'a jamais été si près du but , ça marche presque ...
    Il me trouve bien un lecteur caché, mais pas le bon, avec 128 en décimale convertis en hexadécimale, il devrait me trouver le H caché, là il me trouve le E caché ...

    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
    37
    38
    39
    40
    41
    42
    #include <stdio.h>
    #include <stdlib.h>
    #include <conio.h> // pour le getch();
     
    int decAHex (int);
     
    int main()
    {
        // valeur du registre pour le lecteur H caché
        int valeur=128;
     
        int valeurHex=decAHex(valeur);
     
        int masque=0x01, i;
     
        char lettre=65; // 65 pour la lettre A
     
        for (i=0; i<26; ++i)
        {
            if (valeurHex&masque) // me renvois caché seulement pour E
            {                     // alors que ça devrai être seulement H
                printf("lecteur %c cache\n", lettre);
            }
            else
            {
                printf("lecteur %c visible\n", lettre);
            }
     
            masque<<=i;
            ++lettre;
        }
     
    	getch();
    	return 0;
    }
     
    int decAHex (int nb)
    {
        char nb2[30];
        sprintf(nb2, "%x", nb);
        return strtol(nb2, NULL, 0);
    }
    Déjà, un truc que je ne comprend pas, c'est pourquoi on fais masque<<=i;
    Là, on ne décale pas de la même valeur à chaque fois , pourquoi ?

    Merci.

  20. #20
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 381
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

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

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 381
    Points : 41 582
    Points
    41 582
    Par défaut
    C'est une erreur.
    Un mix entre masque = 1<<i et masque <<= 1...

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

Discussions similaires

  1. Exercice d'addition binaire
    Par ratec dans le forum Pascal
    Réponses: 17
    Dernier message: 06/12/2010, 22h46
  2. Addition binaire
    Par demha dans le forum Pascal
    Réponses: 3
    Dernier message: 06/04/2007, 19h59
  3. [Cognos] Impromptu et Powerplay, je suis paumé
    Par miniquick dans le forum Cognos
    Réponses: 1
    Dernier message: 07/12/2006, 19h26
  4. Addition binaire
    Par mguinot dans le forum Langage
    Réponses: 1
    Dernier message: 24/02/2006, 10h22
  5. Réponses: 3
    Dernier message: 22/09/2005, 10h34

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