Partage
  • Partager sur Facebook
  • Partager sur Twitter

tableau _Bool renvoit des entiers

    19 février 2024 à 19:35:46

    Bonjour,

    Je suis nouveau dans  le langage C/C++ et je suis sur un programme pour démultiplier le nombre de sorties sur l’Arduino.

    Pour ce faire j'ai créer une classe pour manipuler une liste doublement chaînée et une classe pour faire le parallèle entre les sorties de l'arduino et les Elements créés en liste.avec l'utilisation d'un  74HC164 (registre à decalage à entrée séries 8 bits) et un 74HC374(bascule octale de type D).

    ce premier n'utilisant que 3 sorties et acceptant derrière lui autant de 74HC374 que voulu qui n'utilise quant à eux q'une sortie ici.

    ces Element comportent chaqun un tableau de taille 8 et initialiser à "false" .Or ce tableau me renvois des valeurs supérieurs à 1.

    De plus je l'ai tésté ce ce même code sur codeblocks et tout semble bon (niveau valeur,pas niveau construction du programme) et le tableau est initialiser en "false"

    désolé pour la (très) mauvaise structure du code

    //main.cpp
    
    
    

    #include "Sorties_series.h"
    #include "Listes_chainees.hpp"



    void create_new_sorties(int, bool);

    //_num_ref_de_la_sortie est le numero de la premiere sortie que vous rajoutée

    //ligne pour initialiser les sorties registre_bit_suivant, clean, etat_bit_a_intergrer, "_num_ref_de_la_sortie", validation_des_sorties)









    int _num_ref_de_la_sortie = 14;
    Sorties_series sorties_14_a_21;

    void setup()
    {


    //void Sorties_series::configure_sortie_serie( int registre_bit_suivant,int clean, int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1)
    Serial.begin(9600);
    sorties_14_a_21.configure_sortie_serie( 11 , 10 , 12 , _num_ref_de_la_sortie, 9 ,7);

    create_new_sorties(19 , 1);
    }
    void loop()
    {

    }

    void create_new_sorties(int num_de_la_sortie, bool val_a_integrer)
    {
    if (num_de_la_sortie >= _num_ref_de_la_sortie)
    {
    sorties_14_a_21.val_a_ecrire_sur_sorties( num_de_la_sortie , val_a_integrer);

    }
    }
    //listes_chainees.cpp
    

    #include"Arduino.h"
    #include "Sorties_series.h"
    #include "Listes_chainees.hpp"


    //!!!!!!!!!!!!!!penser à initialiser avec NULL car bug!!!!!!!!!!!!!!

    Listes_chainees::Listes_chainees()
    {
    //ctor
    nb_pointeurs_element=0;
    nb_pointeurs_liste=0;
    compteur_de_liste=0;
    }

    Listes_chainees::~Listes_chainees()
    {
    //dtor _num_ref_de_la_sortie
    }


    Liste *Listes_chainees::Creation_Liste()
    {

    Liste *Nouvelle_Liste = NULL;
    Nouvelle_Liste =(Liste*) malloc(sizeof(*Nouvelle_Liste));
    nb_pointeurs_liste++;
    Nouvelle_Liste->precedent=NULL;
    Nouvelle_Liste->suivant=NULL;
    Nouvelle_Liste->index = 0;//ici on met a 0 l'index pour permettre de savoir combien d'elements sont presents dans la liste
    compteur_de_liste++;

    ///*** ici on affecte le premier et le dernier pointeur d'element sur NULL!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
    return Nouvelle_Liste;

    }
    void Listes_chainees::Suppression_Liste(Liste *Liste_EC)
    {

    ///**** Ici on doit dabord verifier qu'il n'y ait plus aucun element avant de supprimer la liste!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
    free(Liste_EC);
    nb_pointeurs_liste--;
    compteur_de_liste--;


    }
    /*void Listes_chainees::insertion(string index1, Liste *Liste_EC)
    {



    }
    void Listes_chainees::insertion(char index1, Liste *Liste_EC)
    {



    }*/


    void Listes_chainees::insertion( int index1, Liste *Liste_EC)
    {

    Element *tempon_element_precedent;
    Element *tempon_element_suivant;
    //Element *conserve_pointeur_element; //vérifier pourquoi il est inutile!!!!!!!!!!!!!!!!
    Element *tempon1 = NULL;
    Element *nouveau = NULL;
    nouveau = ( Element*)malloc(sizeof(*nouveau));
    nb_pointeurs_element++;

    // conserve_pointeur_element = nouveau;
    ///** Pour le premier on verife si le premier et le dernier element sont null!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

    ///*** Ici on gere le premier element!
    if ((Liste_EC->precedent == 0) && (Liste_EC->suivant == 0))
    {
    nouveau->suivant = nouveau;
    nouveau->precedent = nouveau;

    Liste_EC->precedent = nouveau;
    Liste_EC->suivant = nouveau;
    nouveau->index = index1;
    Liste_EC->index = Liste_EC->index + 1;//on actualise le nombre d'elements dans la liste

    //cout <<"************************Creation du premier element************************ \n";
    //cout <<"Nouveau->index="<<nouveau->index<<endl;
    //cout <<"Nouveau->precedent="<<nouveau->precedent<<endl;
    //cout <<" Nouveau="<<nouveau<<endl;
    //cout <<"Nouveau->suivant="<<nouveau->suivant<<endl;
    //cout <<"************************Fin creation du premier element***************************** \n";


    return ;
    }
    //ici on peut affecter avec une fonction
    tempon1=Liste_EC->precedent;// on recupere le premier element de la liste

    do

    {
    if (index1>(tempon1->index)) //on recherche ou on peut l'intercaler
    {
    tempon1 = tempon1->suivant;
    //cout<<"\n on passe au suivant "<< endl;


    }
    //si il est deja existant alors on change sa valeur pour le mettre en dernier
    if ((index1==(tempon1->index)) )
    {
    nouveau->index=index1;//on incremente d'un l'index du dernier element de la liste puisque l'index etait erroné
    tempon_element_precedent=tempon1;//on recupere l'element precedent du dernier element
    tempon_element_suivant=tempon1->suivant;//on recupere l'element suivant du dernier element
    nouveau->suivant = tempon_element_suivant;//on affecte l'element suivant dans le nouveau
    nouveau->precedent = tempon_element_precedent;//on affecte l'element precedent dans le nouveau
    tempon_element_suivant->precedent=nouveau;//on modifie l'element precedent dans l element precedent
    tempon_element_precedent->suivant=nouveau;//on modifie l'element suivant dans l element suivant
    // on n'oublie pas d'incrementer le nombre d'element de la liste
    if ((Liste_EC->suivant)==tempon1)
    {
    Liste_EC->suivant=nouveau;
    }

    Liste_EC->index = Liste_EC->index + 1;

    break;
    /**il faut modifier le suivant ou le precedent de la liste en colurs!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!*/
    }
    if (index1>(Liste_EC->suivant->index))
    {
    tempon1=Liste_EC->suivant ;//on recupere le dernier element de la liste

    nouveau->index=index1;//on incremente d'un l'index du dernier element de la liste puisque l'index etait erroné
    tempon_element_precedent=tempon1;//on recupere l'element precedent du dernier element
    tempon_element_suivant=tempon1->suivant;//on recupere l'element suivant du dernier element
    nouveau->suivant = tempon_element_suivant;//on affecte l'element suivant dans le nouveau
    nouveau->precedent = tempon_element_precedent;//on affecte l'element precedent dans le nouveau
    tempon_element_suivant->precedent=nouveau;//on modifie l'element precedent dans l element precedent
    tempon_element_precedent->suivant=nouveau;//on modifie l'element suivant dans l element suivant
    Liste_EC->suivant=nouveau;//on modifie le dernier element de la liste
    // on n'oublie pas d'incrementer le nombre d'element de la liste
    Liste_EC->index = Liste_EC->index + 1;
    break;
    }

    if (index1<(tempon1->index))
    {
    //"cas ou on intercale "<< endl;
    tempon_element_precedent=tempon1->precedent;//on recupere l'element precedent du dernier element
    tempon_element_suivant=tempon1;//on recupere l'element suivant du dernier element
    nouveau->index=index1;
    nouveau->suivant = tempon_element_suivant;//on affecte l'element suivant dans le nouveau
    nouveau->precedent = tempon_element_precedent;//on affecte l'element precedent dans le nouveau
    tempon_element_suivant->precedent=nouveau;//on modifie l'element precedent dans l element precedent
    tempon_element_precedent->suivant=nouveau;//on modifie l'element suivant dans l element suivant
    // on n'oublie pas d'incrementer lecout<<"<tempon->precedent = "<<tempon->precedent<<endl; nombre d'element de la liste
    if ((Liste_EC->precedent->index)>index1)
    {
    Liste_EC->precedent=nouveau;
    }
    Liste_EC->index = Liste_EC->index + 1;
    //cout <<"************************Creation d'un element avec index a intercaler************************ \n";
    //cout <<"Nouveau->index="<<nouveau->index<<endl;
    //cout <<"Nouveau->precedent="<<nouveau->precedent<<endl;
    //cout <<" Nouveau="<<nouveau<<endl;
    //cout <<"Nouveau->suivant="<<nouveau->suivant<<endl;
    //cout <<"************************Fin creation d'un element avec index a intercaler**************************** \n";

    //et TOC ,on a inseré un element au milieu!

    break;
    }

    }while(true);//tempon1==Liste_EC->precedent);

    }

    void Listes_chainees::cherche_element_a_trouver( int place , Liste *Liste_EC)
    {

    Element *element_a_chercher = Liste_EC->precedent;

    do
    {

    element_a_chercher = element_a_chercher->suivant;

    }while(Liste_EC->precedent->index >= place);
    }

    Element *Listes_chainees::recuperation_d_un_element(int place, Liste *Liste_EC)
    {

    Element *element_recuperer = Liste_EC->precedent;

    do
    {

    element_recuperer = element_recuperer->suivant;

    }while(element_recuperer->index != place);

    return (element_recuperer);

    }

    void Listes_chainees::insertion_de_plusieurs_elements(int nombre_d_element, int index_du_premier, Liste *Liste_EC)
    {
    ///** etudier l'utilisation et la realisation de cette fonction........
    int tempon = 0;
    //struct Element *conserve_pointeur_element = NULL;
    //struct Element *tempon1 = NULL;

    tempon = 0;

    do
    {
    insertion(index_du_premier, Liste_EC);
    tempon++;
    index_du_premier++;

    }while(tempon < nombre_d_element);

    }


    /*void Listes_chainees::affichage_de_la_liste(Liste *Liste_EC)
    {

    Element *a_afficher = Liste_EC->precedent;
    do
    {
    cout<<"\n l'index est egal a "<<a_afficher->index<<endl;
    cout<<"adresse du pointeur precedent est : "<< a_afficher->precedent <<endl;
    cout<<"adresse du pointeur est : "<< a_afficher<<endl ;
    cout<<"adresse du pointeur suivant est : "<< a_afficher->suivant<<endl ;

    a_afficher = a_afficher->suivant;

    }while(Liste_EC->precedent != a_afficher);

    cout<<"*****************************adresse du pointeur precedent dans la liste est : "<< Liste_EC->precedent <<endl;
    cout<<"*****************************adresse du pointeur suivant dans la liste est : "<< Liste_EC->suivant <<endl;


    cout<<"\n\n****fin affichage***********"<<endl;

    }*/

    void Listes_chainees::supression_d_un_element(int index1, Liste *Liste_EC)
    {

    Element *tempon1 = Liste_EC->precedent;
    Element *a_suprimmer = NULL;
    Element *tempon_element_precedent;
    Element *tempon_element_suivant;
    // recherche du pointeur a suprimer penser a relancer la recherche si il y a plusieurs fois le meme index
    do
    {
    if (index1==tempon1->index)
    {
    a_suprimmer=tempon1;
    //cout<<"a_suprimmer="<<a_suprimmer <<endl;
    tempon_element_precedent=tempon1->precedent;
    tempon_element_suivant=tempon1->suivant;
    tempon_element_precedent->suivant=tempon_element_suivant;
    tempon_element_suivant->precedent=tempon_element_precedent;
    free(a_suprimmer);
    nb_pointeurs_element--;
    Liste_EC->index=(Liste_EC->index)-1;
    }
    tempon1=tempon1->suivant;
    }while(tempon1!=Liste_EC->precedent);

    }

    void Listes_chainees::supression_de_toute_la_liste ( Liste *Liste_EC)
    {
    Element *a_suprimmer = Liste_EC->suivant;//Recuperation du dernier element de la liste
    while((a_suprimmer) != Liste_EC->precedent)
    {
    a_suprimmer = Liste_EC->suivant ;
    Liste_EC->suivant = a_suprimmer->precedent;
    free (a_suprimmer);
    nb_pointeurs_element--;
    }

    }
    /*
    void Listes_chainees::affichage_d_un_element(int index1, Liste *Liste_EC)
    {
    Element *a_afficher = Liste_EC->suivant;
    do
    {
    a_afficher = a_afficher->precedent;

    }while(a_afficher->index != index1);
    cout<<"\nl'index est egal a "<<a_afficher->index<<endl;
    cout<<"adresse du pointeur suivant est : "<< a_afficher->suivant<<endl ;
    cout<<"adresse du pointeur est : "<< a_afficher<<endl ;
    cout<<"adresse du pointeur precedent est : "<< a_afficher->precedent <<endl;
    cout<<"\n***********fin de l'affichage d un element***************" <<endl;
    }*/

    //Listes_chainees.hpp #include"Arduino.h" #include "Sorties_series.h" #ifndef LISTES_CHAINEES_H #define LISTES_CHAINEES_H typedef struct Element Element; struct Element { int index; Element *precedent; Element *suivant; int validation_des_sorties_ds_element = 9; bool les_8_sorties[8]#include <iostream> using namespace std; #include "Sorties_series.h" #include "Listes_chainees.h" /*sorties_series sorties_22_a_29(0, 0, 0, 22); sorties_series sorties_30_a_37(0, 0, 0, 30); sorties_series sorties_38_a_45(0, 0, 0, 38); sorties_series sorties_46_a_54(0, 0, 0, 46);*/ void create_new_sorties(int, bool); //_num_ref_de_la_sortie est le numero de la premiere sortie que vous rajoutée //ligne pour initialiser les sorties registre_bit_suivant, clean, etat_bit_a_intergrer, "_num_ref_de_la_sortie", validation_des_sorties) int _num_ref_de_la_sortie = 14; Sorties_series sorties_14_a_21; int main(int argc,const char * argv[]) { //void Sorties_series::configure_sortie_serie( int registre_bit_suivant,int clean, int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1) sorties_14_a_21.configure_sortie_serie( 11 , 10 , 12 , _num_ref_de_la_sortie, 9 ,7); cout<<"changement de tableau"<<endl; cout<<"changement de tableau"<<endl; create_new_sorties(17 , 1); //create_new_sorties(18 , 1); //create_new_sorties(19 , 1); cout<<"changement de tableau"<<endl; cout<<"changement de tableau"<<endl; create_new_sorties(29 , 1); cout<<"changement"<<endl; return(0); } void create_new_sorties(int num_de_la_sortie, bool val_a_integrer) { if (num_de_la_sortie >= _num_ref_de_la_sortie) { sorties_14_a_21.val_a_ecrire_sur_sorties( num_de_la_sortie , val_a_integrer); } } = {false}; /* les_8_sorties[0] = 0; les_8_sorties[1] = 0; ///,0,0,0,0,0,0,0 les_8_sorties[2] = 0; les_8_sorties[3] = 0; les_8_sorties[4] = 0; les_8_sorties[5] = 0; les_8_sorties[6] = 0; les_8_sorties[7] = 0;*/ }; typedef struct Element Liste ; class Listes_chainees { public: Listes_chainees(); virtual ~Listes_chainees(); int comptexit=0; Element test(); void supression_d_un_element( int, Liste*); void supression_de_toute_la_liste(Liste*); //void affichage_de_la_liste(Liste*); void affichage_d_un_element(int, Liste*); void insertion_de_plusieurs_elements( int, int, Liste* ); void cherche_element_a_trouver( int, Liste*); Element *recuperation_d_un_element(int , Liste*); void insertion(int , Liste*); //void insertion(char , Liste*); //void insertion(string , Liste*); //void insertion(double , Liste*); //void insertion(float , Liste*); Liste *Creation_Liste(); void Suppression_Liste(Liste *); int nb_pointeurs_element; int nb_pointeurs_liste; /** IL faut supprimer le pointeur de liste dans le main **/ protected: private: int compteur_de_liste; /*struct Element conserve_pointeur_element1; struct Element *P_conserve_pointeur_element1 = &conserve_pointeur_element1; // struct Element *P_conserve_pointeur_element = liste.suivant; struct Element tempon_element_precedent1; struct Element *P_tempon_element_precedent1 = &tempon_element_precedent1; //struct Element *tempon_element_precedent = liste.suivant; struct Element tempon_element_suivant1; struct Element *P_tempon_element_suivant1 = &tempon_element_precedent1; //struct Element *tempon_element_suivant = liste.suivant;*/ }; #endif // CLASSES_CHAINEES_H /**si il est deja existant alors on change sa valeur pour le mettre en dernier if ((index1==(tempon1->index)) ) { cout<<"cas d'une valeur identique "<< endl; cout<<"Liste_EC->suivant->index= " <<Liste_EC->suivant->index<<endl; tempon1=Liste_EC->suivant ;//on recupere le dernier element de la liste nouveau->index=((tempon1->index)+1);//on incremente d'un l'index du dernier element de la liste puisque l'index etait erroné tempon_element_precedent=tempon1->precedent;//on recupere l'element precedent du dernier element tempon_element_suivant=tempon1->suivant;//on recupere l'element suivant du dernier element nouveau->suivant = tempon_element_suivant;//on affecte l'element suivant dans le nouveau nouveau->precedent = tempon_element_precedent;//on affecte l'element precedent dans le nouveau tempon_element_suivant->precedent=nouveau;//on modifie l'element precedent dans l element precedent tempon_element_precedent->suivant=nouveau;//on modifie l'element suivant dans l element suivant Liste_EC->suivant=nouveau;//on modifie le dernier element de la liste // on n'oublie pas d'incrementer le nombre d'element de la liste Liste_EC->index = Liste_EC->index + 1; cout <<"************************Creation d'un element avec modification de son index ************************ \n"; cout <<"Nouveau->index="<<nouveau->index<<endl; cout <<"Nouveau->precedent="<<nouveau->precedent<<endl; cout <<" Nouveau="<<nouveau<<endl; cout <<"Nouveau->suivant="<<nouveau->suivant<<endl; cout <<"************************Fin creation d'un element avec modification de son index**************************** \n"; break; }**/
    //Sorties_series.hpp
    
    
    
    #ifndef SORTIES_SERIES
    #define SORTIES_SERIES
    
    #include "Arduino.h"
    #include "Listes_chainees.hpp"
    
    
    /******
       compiler (Ctrl + R)
       de téléverser (Ctrl + U)
       de créer un nouveau programme (Ctrl + N)
       d'ouvrir un programme (Ctrl + O)
       de sauvegarder le programme en cours (Ctrl + S)
       ainsi qu'un moniteur série (Ctrl + Maj + M).
     ******/
     //!!!!!!!!!ne pas creer la liste ici mais directement dans la classe sinon message:multiple definition of!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!//
    
    
    
    class Sorties_series
    {
      public:
        Listes_chainees Liste_chainee;
        Liste *MaPremierListe = Liste_chainee.Creation_Liste();
        Sorties_series();
        ~Sorties_series();
        void configure_sortie_serie(int, int, int, int, int);                     //permet d'initialiser les sorties
        void configure_sortie_serie(int, int, int, int, int, int);
        void configure_sortie_serie(int, int, int, int, int, int, int);
        void configure_sortie_serie(int, int, int, int, int, int, int, int);
        //int trouver_le_bon_element(int );
        void val_a_ecrire_sur_sorties (int, bool);                //a la fin il relance le tableau qu'il doit récupérer et après y avoir changé la valeur au niveau de la sortie souhaité
        void pilotage_bascule(int);                                   //gère le relancement du tableau en utilisant les 2 foctions qui suivent incremente_registre() et valide_sorties()
        // int select_num_ref_de_la_sortie(int);
        void incremente_registre();
        void valide_sorties();
      private:
      int conserve_num_ref = 1;
    
      int tempon1 = 0;
        int _clean;
        int sortie = 0;
        //_Bool led[8] = {0};
        int validation_des_sorties;
        int _nb_de_sorties_rajoutes;
       // int num_ref_de_la_sortie;
        int _validation_des_sorties;
        int _registre_bit_suivant;
        int _etat_bit_a_intergrer;
        int _num_ref_de_la_sortie;
    
    
    
    };
    /***************************
      pour un arduino uno sorties integrées en digital jusqu'à la 13eme sortie
      num_ref_de_la_sortie:
      on a donc par paquet de huit
      1er element  14 et 14 + 8 = 22
      2eme element 22 et 22 + 8 = 30
      3eme element 30 et 30 + 8 = 38
      4eme element 38 et 38 + 8 = 46
      5eme element 46 et 46 + 8 = 54
    **************************/
    
    #endif
    //Sorties_series.cpp
    
    
    
    #include "Sorties_series.h"
    
    
    
    /* Trouver une solution pour que la premiere sortie de chaque "sortie serie" change en fonction du type de carte*/
    /******
       compiler (Ctrl + R)
       de téléverser (Ctrl + U)
       de créer un nouveau programme (Ctrl + N)
       d'ouvrir un programme (Ctrl + O)
       de sauvegarder le programme en cours (Ctrl + S)
       ainsi qu'un moniteur série (Ctrl + Maj + M).
     ******/
    
    Sorties_series::Sorties_series()
    {
    
    }
    void Sorties_series::configure_sortie_serie( int registre_bit_suivant,int clean, int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1)
    {
       Element *tempon = NULL;
      _clean = clean;
      _registre_bit_suivant = registre_bit_suivant;
      _etat_bit_a_intergrer = etat_bit_a_intergrer;
      _num_ref_de_la_sortie = num_ref_de_la_sortie;
      /* pinMode(_clean , OUTPUT );
      pinMode(_num_ref_de_la_sortie , OUTPUT);
      pinMode(_registre_bit_suivant , OUTPUT);
      pinMode(_etat_bit_a_intergrer , OUTPUT);*/
      Liste_chainee.insertion(0, MaPremierListe);
      tempon = Liste_chainee.recuperation_d_un_element(0 , MaPremierListe);
      tempon->validation_des_sorties_ds_element = validation_des_sorties1;
      _nb_de_sorties_rajoutes = 1;
    }
    void Sorties_series::configure_sortie_serie( int registre_bit_suivant,int clean , int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1, int validation_des_sorties2)
    {
        Element *tempon = NULL;
        configure_sortie_serie( registre_bit_suivant,clean, etat_bit_a_intergrer, num_ref_de_la_sortie, validation_des_sorties1);
        Liste_chainee.insertion(1, MaPremierListe);
        tempon = Liste_chainee.recuperation_d_un_element(1 , MaPremierListe);
        tempon->validation_des_sorties_ds_element = validation_des_sorties2;
        _nb_de_sorties_rajoutes = 2;
    
    }
    void Sorties_series::configure_sortie_serie( int registre_bit_suivant,int clean, int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1, int validation_des_sorties2, int validation_des_sorties3)
    {
    Element *tempon = NULL;
      configure_sortie_serie( registre_bit_suivant,clean, etat_bit_a_intergrer, num_ref_de_la_sortie, validation_des_sorties1, validation_des_sorties2);
      Liste_chainee.insertion(2, MaPremierListe);
      tempon = Liste_chainee.recuperation_d_un_element(2 , MaPremierListe);
      tempon->validation_des_sorties_ds_element = validation_des_sorties3;
      _nb_de_sorties_rajoutes = 3;
    }
    void Sorties_series::configure_sortie_serie(int registre_bit_suivant, int clean, int etat_bit_a_intergrer, int num_ref_de_la_sortie, int validation_des_sorties1, int validation_des_sorties2, int validation_des_sorties3, int validation_des_sorties4)
    {
        Element *tempon = NULL;
        configure_sortie_serie( registre_bit_suivant,clean, etat_bit_a_intergrer, num_ref_de_la_sortie, validation_des_sorties1, validation_des_sorties2, validation_des_sorties3);
        Liste_chainee.insertion(3, MaPremierListe);
        tempon = Liste_chainee.recuperation_d_un_element(3 , MaPremierListe);
        tempon->validation_des_sorties_ds_element = validation_des_sorties4;
      _nb_de_sorties_rajoutes = 4;
    }
    Sorties_series::~Sorties_series()
    {
    
    
    }
    
    
    /*int Sorties_series::trouver_le_bon_element(int place)
    {
    
    
    }*/
    
    void Sorties_series::val_a_ecrire_sur_sorties(int num_de_la_sortie, bool etat)
    {
        Element *tempon = NULL;
       digitalWrite(_clean, HIGH);
    
        int tempon_num_ref_de_la_sortie = _num_ref_de_la_sortie;
        int tempon_place_dans_tableau = num_de_la_sortie - _num_ref_de_la_sortie + 1;
        int numero_de_l_element = 0;
        int place = 0;
    
    
    
      //numero_de_l_element = trouver_le_bon_element(num_de_la_sortie);                            //666666 je recupere par la fonction la valeur que doit avoir mon index
      place = place - tempon_num_ref_de_la_sortie;
      Serial.print("   _num_ref_de_la_sortie =  ");
      Serial.print(tempon_num_ref_de_la_sortie);
      Serial.print("   num_de_la_sortie =  ");
      Serial.print(num_de_la_sortie);
      Serial.print("   numero_de_l_element =  ");
      Serial.print(numero_de_l_element);
      Serial.print("\n");
    
      while ( tempon_num_ref_de_la_sortie <= num_de_la_sortie)
      {
        tempon_num_ref_de_la_sortie = tempon_num_ref_de_la_sortie + 8;
        numero_de_l_element = numero_de_l_element + 1;
      };
        numero_de_l_element = numero_de_l_element - 1;
                                  //numero_de_l_element est le numero de l'octuple verrou et numero_de_l_element va devoir
                                                                               //correspondre au numero de l'index d'unelement donc je dois soustraire un car avec
                                                                               //les elements je commence a partir de 0 et avec le numero de l'octuple verrou  a partir de 1
      Serial.print("   numero_de_l_element =  ");
      Serial.print(numero_de_l_element);
      Serial.print("\n");
      tempon = Liste_chainee.recuperation_d_un_element(numero_de_l_element , MaPremierListe);
      //777777 je recupere l'addresse de l'element pour pouvoir y amnipuler un tableau
    
        do                                                                                     //999999je cherche la place de ma sortie dans mon tableau
      {
    
        tempon_place_dans_tableau = tempon_place_dans_tableau - 8;
    
      } while (tempon_place_dans_tableau > 0);
    
      tempon_place_dans_tableau = tempon_place_dans_tableau + 8;
     //Serial.print("   tempon_place_dans_tableau =  ");
      //Serial.print(tempon_place_dans_tableau);
      //Serial.print("\n");
    
      tempon->les_8_sorties[tempon_place_dans_tableau - 1] = etat;                             //10 10 10 10 je change l'état de la variable dans mon tableau
    
    
      Serial.print("   _nb_de_sorties_rajoutes =  ");
      Serial.print(_nb_de_sorties_rajoutes);
      Serial.print("\n");
      Serial.print("   _validation_des_sorties =  ");
      Serial.print(_validation_des_sorties);
      Serial.print("\n");
      Serial.print("   _registre_bit_suivant =  ");
      Serial.print(_registre_bit_suivant);
      Serial.print("\n");
      Serial.print("   _etat_bit_a_intergrer =  ");
      Serial.print(_etat_bit_a_intergrer);
      Serial.print("\n");
      pilotage_bascule(numero_de_l_element);
      //validation_des_sorties = 9 ;  //tempon->validation_des_sorties_ds_element
    
      Serial.print("tempon->validation_des_sorties = ");
      Serial.print(validation_des_sorties);
      digitalWrite(_clean, LOW);
      digitalWrite(_clean, HIGH);
      Serial.print("\n");
      Serial.print("fin de l'action");
      Serial.print("\n");
    }
    
    
    
    
    
    void Sorties_series::pilotage_bascule(int tempon1 )
    {
        Element *tempon = NULL;
      int arret = 0;
      //Serial.print("   tempon_insertion 0=  ");
      int numero = 0;
      /*int tempon = 0;
      tempon = Liste_chainee.recuperation_d_un_element(tempon1 , MaPremierListe);
      digitalWrite(_clean, HIGH);
      do
      {
    
      digitalWrite(_etat_bit_a_intergrer,tempon->les_8_sorties[tempon]);
      digitalWrite(bascule_suivant, HIGH);
      digitalWrite(bascule_suivant, LOW);
      Serial.print("led 0 = ");
      //Serial.print(tempon->les_8_sorties[0]);
      Serial.print("\n");
      digitalWrite(validation_des_sorties, HIGH);
      digitalWrite(validation_des_sorties, LOW);
      tempon++;
    
      }while(tempon < 8);
      digitalWrite(_clean, LOW);
      digitalWrite(_clean, HIGH);
      */
      if (arret == 0)
      {
        while (tempon1 < _nb_de_sorties_rajoutes)
        {
    
          tempon = Liste_chainee.recuperation_d_un_element(tempon1 , MaPremierListe);
          while (numero < 8)
          {
    
            digitalWrite(_etat_bit_a_intergrer , tempon->les_8_sorties[numero]);
            incremente_registre();
            digitalWrite(11, HIGH);
            digitalWrite(11, LOW);
            Serial.print("led 0 = ");
            Serial.print( tempon->les_8_sorties[numero]);
            Serial.print("\n");
            valide_sorties();
            digitalWrite(9, HIGH);
            digitalWrite(9, LOW);
            numero++;
          };
            
           // digitalWrite( 9 , HIGH);  //tempon->validation_des_sorties_ds_element
           // delay(1000);
           // digitalWrite(9, LOW);   //tempon->validation_des_sorties_ds_element
           //Serial.print("   tempon_insertion 0=  ");
    
        tempon1++;
        };
      }
      if (arret == 0)
      {
        arret = 1;
      }
    
      // digitalWrite(_validation_des_sorties, HIGH);
    }
    void Sorties_series::incremente_registre()
    {
      digitalWrite(_registre_bit_suivant, HIGH);
      digitalWrite(_registre_bit_suivant, LOW);
    }
    void Sorties_series::valide_sorties()
    {
      digitalWrite(_validation_des_sorties, HIGH);
      digitalWrite(_validation_des_sorties, LOW);
    }
    
    

    Merci beaucoup de votre aide et dites le moi si je dois corriger des éléments qui vous on perturbé.




    • Partager sur Facebook
    • Partager sur Twitter
      26 février 2024 à 17:22:17

      Hello,

      C'est plus un problème de c++ qu'un problème électronique. Poste ton message dans le forum c++.

      • Partager sur Facebook
      • Partager sur Twitter

      On écrit "j'ai tort", pas "tord" qui est le verbe "tordre" à la 3ème personne de l'indicatif présent

        26 février 2024 à 17:53:43

        Bonjour, plutôt que de créer un doublon, signaler le sujet à la modération pour demander un déplacement.

        Je déplace le sujet.

        Déplacement vers un forum plus approprié

        Le sujet est déplacé de la section  Électronique vers la section Langage C++

        • Partager sur Facebook
        • Partager sur Twitter
          26 février 2024 à 18:13:38

          PierreClaude3 a écrit:

          Or ce tableau me renvois des valeurs supérieurs à 1.

          Quel tableau ? Quelle ligne ?

          PierreClaude3 a écrit:

          dites le moi si je dois corriger des éléments qui vous on perturbé.

          La totalité du code est perturbante.
          • Partager sur Facebook
          • Partager sur Twitter
            15 mars 2024 à 10:46:12

            Bonjour gbdivers,

            le tableau est celui créé dans le fichier "Listes_chainees.hpp", dans la structure "Element" ,ligne 17.

            dans le fichier "Sorties_series.cpp" ,ligne 191 à 206, lorsque je demande à l'arduino de m'afficher les valeurs sur le moniteur série(lignes 199,200,201).

            merci d'avoir regardé et encore désolé pour la structure du code.

            -
            Edité par PierreClaude3 15 mars 2024 à 10:48:23

            • Partager sur Facebook
            • Partager sur Twitter
              15 mars 2024 à 12:04:58

              Si tu conviens que la structure du code n'est pas bonne, c'est que tu as une idée de comment ça pourrait être mieux.

              Reste plus qu'a l'arranger.

              PS le choix des structures de données. Un _Bool est représenté sur un entier d'au moins 8 bits. Donc un tableau de 8  booléens occupe 64 bits dont 56 ne servent à rien.

              La tradition (Et le bon goût) est plutôt d'utiliser un seul char pour 8 bits, et d'agir dessus avec des masques binaires.

              Pour déclarer et initialiser un tableau de 8 bits à faux : unsigned char tableau = 0;

              Pour mettre le bit 3 à vrai :  tableau |= (1 << 3);

              Pour mettre le bit 4 à faux : tableau &= ~(1 << 4);

              Pour tester si le bit 2 est a vrai : if (tableau & (1 << 2)) { ....}

              PS2 POURQUOI s'embêter avec une liste chaînée là où un vector ou un array ferait le boulot, avec du code à la fois beaucoup plus simple et plus rapide ? Le nombre de circuits varie pendant l'exécution ?

              -
              Edité par michelbillaud 15 mars 2024 à 12:38:24

              • Partager sur Facebook
              • Partager sur Twitter
                15 mars 2024 à 19:37:31

                Pour inverser le bit 5: tableau ^= (1<<5);

                Je ne sais pas tout à fait le but du montage, mais il me semble qu'il existe un circuit qui prend 3 bits en input et qu'il active une ligne parmi 8 lignes en sortie.

                On a la même chose pour un 4 bits sur 16 lignes.

                Chercher: 3 bits to 8 lines multiplexer.

                -
                Edité par PierrotLeFou 15 mars 2024 à 19:49:34

                • Partager sur Facebook
                • Partager sur Twitter

                Le Tout est souvent plus grand que la somme de ses parties.

                  15 mars 2024 à 22:07:16

                  PierrotLeFou a écrit:

                  Pour inverser le bit 5: tableau ^= (1<<5);

                  Je ne sais pas tout à fait le but du montage, mais il me semble qu'il existe un circuit qui prend 3 bits en input et qu'il active une ligne parmi 8 lignes en sortie.

                  On a la même chose pour un 4 bits sur 16 lignes.

                  Chercher: 3 bits to 8 lines multiplexer.

                  -
                  Edité par PierrotLeFou il y a environ 1 heure

                  C'est un décodeur 3 vers 8.  https://www.mouser.fr/c/semiconductors/logic-ics/encoders-decoders-multiplexers-demultiplexers/?logic%20family=74HC

                  Avec deux, on peut faire un 4 vers 16 en jouant avec les 3 entrées "enable". Le 4ieme bit d'adresse va vers une sélection sur un circuit, et une sélection inversée sur l'autre

                  Ps Un multiplexeur , ça prendrait 3 bits d'adresse, 8 de données et ça recopierait un bit de donnée sur la sortie.

                  -
                  Edité par michelbillaud 16 mars 2024 à 8:05:21

                  • Partager sur Facebook
                  • Partager sur Twitter
                    20 mars 2024 à 13:41:43

                    c'est difficile de faire du reverse engineering sur du code source qui a été pas mal mutilé pendant la copie sur le forum (il manque des lignes, il y a deux main...), et qui fait quand même dans les 600 lignes...

                    Reprenons par le début. Que veut-on faire ?  J'ai l'impression qu'il s'agit de créer un montage avec 54 sorties, sur lesquelles on peut agir par un truc comme

                    Montage m{.....};   // initialisation
                    
                    m.set(numero_sortie, nouvel_etat);
                    

                    Les sorties 1 à 13 correspondant directement à celles de l'arduino, les autres (à partir de 14) aux sorties de 5 bascules D octales.

                    Hypothèses sur le montage (si je devais faire un truc comme ça)

                    Pour mettre des données dans une bascule octale, on commence par charger un octet dans un registre à décalage 8 bits, puis on active l'entrée d'horloge de la bascule.

                    Les sorties du registre à décalage vont sur un bus de données auquel sont raccordées les bascules D.

                    Avec ça, il nous faut

                    • 2 sorties de l'arduino pour clock et data_in du registre à décalage
                    • 1 sortie arduino pour le clock de chaque bascule (ce qui nous en fait 5)
                    Pour le code de la classe Montage

                    • un tableau de 5 octets pour mémoriser les données de chaque bascule octale
                    • les numéros des 2 sorties pour le pilotage du registre à décalage
                    • un tableau de numéros des sorties qui activent chaque bascule (broche_horloge)

                    et en quelques lignes de code ça devrait le faire.

                    void Montage::set(unsigned int numero_sortie, int etat)
                    {
                       if (numero_sortie < 14) {
                            digitalWrite(numero_sortie, etat);
                            return;
                       }
                    
                       auto numero_bit     = numero_sortie - 14: 
                       auto numero_bascule = numero_bit / 8;
                       auto index_bit      = numero_bit % 8;
                    
                       // 1. forcer le bit index_bit de tableau[numero_bascule]
                       // à 0 ou 1 selon etat
                    
                       // 2 charger tableau[numero_bascule]
                       // dans le registre à décalage
                    
                       // 3 envoyer un bip sur broche_horloge[numéro_bascule]
                    
                       thats_all(); 
                    }



                    PS : Y aurait quand même plus simple : cascader des registres à décalage (entrée série, sortie parallèle) genre 74HC595 https://fr.wikipedia.org/wiki/Circuit_int%C3%A9gr%C3%A9_74595

                    Ça fait un circuit en moins et ça réduit à 3 le nombre de sorties arduino nécessaires

                    • 2 pour l'entrée des données (SER premier circuit, SRK communs)
                    • 1 pour le transfert en sortie (RCK commun)

                    à qui on peut ajouter une remise à 0 et activation des sorties.

                    Avantage : y a moins de circuits (juste les 5 74HC595) qui ont moins de pattes (16 au lieu de 20 pour les bascules D)
                    Peut être un inconvénient si il y a une problématique de rapidité : pour changer une sortie, il faut transférer les 5 x 8 = 40 bits en série.

                    -
                    Edité par michelbillaud 21 mars 2024 à 12:05:17

                    • Partager sur Facebook
                    • Partager sur Twitter
                      28 mars 2024 à 13:04:16

                      bonjour Michelbillaud,

                      merci pour les réponses mais j'ai fait ces listes chainées pour pouvoir les réutilisées pus tard dans d'autre programmes.Je les utilisent juste là pour m'entrainer.

                      De plus, j’essaye de "consommer" les composants qui ne me servent à rien et que j'ai en stock et, sur la carte, le nombre de sorties (donc de composants) peut varier (en fonction des besoins). cette carte étant utilisé pour augmenter le nombre de sorties sur l’Arduino (uno). Et je ne peux pas avoir de confusion en utilisant un char (dont la structure que vous avez présenté semble assez compliquée) ?

                      merci encore pour votre aide,

                      joyeuses Pâques.

                      • Partager sur Facebook
                      • Partager sur Twitter
                        29 mars 2024 à 8:59:44

                        Maintenant que les listes chaînées ont été écrites, c'est une bonne idée de les (ré)utiliser dans des programmes qui en ont besoin.

                        Donc de les enlever de celui ci, où ça n'amène que des complications (et un gaspillage monstrueux  de ressources) dont on peut facilement se dispenser.

                        Comme disait quelqu'un, un gentleman c'est quelqu'un qui sait jouer de l'accordéon, et s'en abstient. Pareil pour les programmeurs et les listes chaînées.

                        > je ne peut pas avoir de confusion ?

                        Quelle confusion par exemple ?


                        PS: ce n'est pas difficile de construire une structure de données qui représente un tableau de booléens en les casant dans des entiers considérés comme tableaux de bits.


                        Exemple, sous forme d'une classe paramétrée, utilisation d'un tableau de 33 bits

                        void test_get_set()
                        {
                            BoolArray<33> a;
                        
                            a.set(0);
                            a.set(1);
                            a.set(5);
                            a.set(6);
                            a.set(32);
                        
                            a.reset(0);
                            a.reset(5);
                        
                            std::cout << "Bits à 1 : ";
                            for (int i = 0; i < 33; i++) {
                                if (a.get(i)) std::cout << i << " ";
                            }
                            std::cout << std::endl;
                        }

                        Quand ça s'exécute ça dit que

                        g++ -std=c++20 -Wall -Wextra -pedantic -Werror -Wno-unused -g    prog.cc   -o prog
                        ./prog
                        Bits à 1 : 1 6 32 
                        

                         => ok.

                        Le code de la classe (template)

                        template<int size> class BoolArray
                        {
                            uint8_t m_array[(size + 7) / 8] = {0};
                        
                        public:
                        
                            void set(unsigned int i)
                            {
                                m_array[i / 8] |=  1 << (i % 8);
                            }
                        
                            void reset(unsigned int i)
                            {
                                m_array[i / 8] &= ~(1 << (i % 8));
                            }
                        
                            void set(unsigned int i, bool value)
                            {
                                if (value) {
                                    set(i);
                                } else {
                                    reset(i);
                                }
                            }
                        
                            bool get(unsigned int i)
                            {
                                return m_array[i / 8] &  (1 << (i % 8));  // conversion en bool
                            }
                           
                        };


                        Quelques inlines ne feraient pas de mal.


                        En exercice (pas faciles quand on sait pas)

                        • surcharges de [] pour pouvoir faire   a[indice] = booleen    et   if (a[indice]) ....
                        • parcours du tableau   for (bool b: a) { ....}

                        -
                        Edité par michelbillaud 29 mars 2024 à 10:43:22

                        • Partager sur Facebook
                        • Partager sur Twitter
                          29 mars 2024 à 10:37:05

                          Bonjour Michelbillaud,

                          le type char n'est-il pas spécifique aux caractères ?

                          Et ce que je ne comprend pas c'est le fait que un tableau, dont les valeurs à l'interieur ne peuvent être que 0 ou 1 grâce au type  "_Bool", me renvoi des entiers supérieur à 1.

                          merci d'avoir répondu aussi vite

                          • Partager sur Facebook
                          • Partager sur Twitter
                            29 mars 2024 à 11:38:14

                            PierreClaude3 a écrit:

                            Bonjour Michelbillaud,

                            le type char n'est-il pas spécifique aux caractères ?

                            Et ce que je ne comprend pas c'est le fait que un tableau, dont les valeurs à l'interieur ne peuvent être que 0 ou 1 grâce au type  "_Bool", me renvoi des entiers supérieur à 1.

                            merci d'avoir répondu aussi vite


                            Le type char est mal nommé en C/C++, ça date d'une époque où les informaticiens voyaient les caractères en codage ASCII 7 bits ou EBCDIC 8 bits.   Et pour ça des petits entiers suffisaient (8 bits en général, parfois 9 sur les machines à mot de 18 ou 36 bits)).  Ils auraient mieux fait de distinguer  "byte" et "char". Mais en C, ils voulaient pas s'emmerder, alors, allons-y Alonzo, on dit que les entiers sur un octet c'est des caractères.

                            Sans d'ailleurs décider si les char c'était des entiers signés ou pas. Ce qui change pas mal de choses.

                            Les _Bool, c'est un rajout tardif à la norme C pour pallier le manque de booléens. Ils ne sont pas représentés sur 1 bit. La norme C https://open-std.org/JTC1/SC22/WG14/www/docs/n3220.pdfnote en bas de la page 105 dit que le nombre de bits d'un bool est AU MOINS égal à celui d'un char  (CHAR_BITS)

                            Et il peut traîner n'importe quoi dans les 8 bits si ça n'a pas été initialisé : comportement indéfini.  C'est probablement ce qui vous arrive, mais votre code est trop touffu pour que je me lance à chercher où précisément. Faites-le compiler avec la détection de tous les warnings, ça sera déjà ça.


                            PS: suis arrivé à bricoler les surcharges pour utiliser la notation "crochets"

                            void test_brackets()
                            {
                                BoolArray<33> a;
                            
                                std::cout << "test_brackets" << std::endl;
                                a[0] = true;
                                a[1] = true;
                                a[5] = true;
                                a[6] = true;
                            
                                a[0]  = false;
                                a[32] = true;
                                a[5] = false;
                            
                                std::cout << "Bits à 1 : ";
                                for (int i = 0; i < 33; i++) {
                                    if (a[i]) std::cout << i << " ";
                                }
                                std::cout << std::endl;
                            

                            Idées :

                            • une expression avec crochets comme a[i] retourne un objet qui indique la position d'un bit dans un BoolArray. C'est le type BoolArrayPosition
                            • l'affectation d'un booléen à un BoolArrayPosition modifie le BoolArray
                            • La conversion d'un BoolArrayPosition en bool retourne le bit correspondant
                            C'est un peu galère parce que les deux classes templates se font des références mutuelles, donc il faut faire des prédéclarations, etc. Je déteste C++.

                            emplate<int size> class BoolArrayPosition;
                            
                            
                            template<int size> class BoolArray
                            {
                                uint8_t m_array[(size + 7) / 8] = {0};
                            
                            public:
                            
                                // get, set, reset comme avant
                                BoolArrayPosition<size> operator[](unsigned int i);
                            };
                            
                            template<int size> class BoolArrayPosition
                            {
                                BoolArray<size> &m_array;
                                unsigned m_i;
                            public:
                                BoolArrayPosition(BoolArray<size> &array, unsigned int i)
                                    : m_array{array}
                                    , m_i{i} {}
                            
                                bool operator=(bool value)
                                {
                                    m_array.set(m_i, value);
                                    return value;
                                }
                            
                                operator bool() const {
                                    return m_array.get(m_i);
                                }
                            
                            };
                            
                            template<int size> BoolArrayPosition<size> BoolArray<size>::operator[](unsigned int i)
                            {
                                return BoolArrayPosition<size>{*this, i};
                            }
                            




                            -
                            Edité par michelbillaud 29 mars 2024 à 11:50:45

                            • Partager sur Facebook
                            • Partager sur Twitter
                              29 mars 2024 à 11:45:57

                              Arduino préconise (suggère fortement) d'utiliser byte pour des octets, et de n'utiliser char que pour des caractères en effet https://www.arduino.cc/reference/fr/language/variables/data-types/char/

                              un booléen Arduino est codé sur un octet, false valant 0 et toute autre valeur est équivalente à true.

                              https://www.arduino.cc/reference/fr/language/variables/constants/constants/ 

                              • Partager sur Facebook
                              • Partager sur Twitter
                                29 mars 2024 à 12:00:13

                                > Arduino, toute autre valeur est équivalente à true.

                                Arduino, c'est du C++ sans une partie de la bibliothèque standard.

                                L'affectation à une variable booléenne provoque une normalisation, exemple en C

                                include <stdio.h>
                                
                                int main() {
                                	_Bool b;
                                	b = 33;
                                	printf("%d\n", b);
                                	return 0;
                                }
                                

                                qui affiche 1.

                                Ou encore

                                #include <stdbool.h>
                                
                                bool b(int i) {
                                	return i;
                                }
                                

                                que le compilateur convertit en

                                	testl	%edi, %edi
                                	setne	%al
                                	ret
                                

                                Doc: testl : "et" du registre edi avec lui même pour positionner les indicateurs

                                SETNE/SETNZ - Set if Not Equal / Set if Not Zero (386+)
                                
                                        Usage:  SETNE   dest
                                                SETNZ   dest
                                        Modifies flags: none
                                
                                        Sets the byte in the operand to 1 if the Zero Flag is clear,
                                        otherwise sets the operand to 0.

                                 Ce qui permet d'induire que si il y a n'importe quoi dans un bool, c'est qu'il n'a probablement pas été initialisé (ou alors il y a eu un accès mémoire illégal avec un pointeur tourné zinzin). Mais pas par une affectation.

                                -
                                Edité par michelbillaud 29 mars 2024 à 12:06:42

                                • Partager sur Facebook
                                • Partager sur Twitter
                                  1 avril 2024 à 11:53:14

                                  Comme j'aime bien pisser dans les violons( comme le regretté Kevin Ayers  https://www.youtube.com/watch?v=8xgx0CmHw_k ), développement sur le même thème "tableau de bits" : selon l'architecture, il peut être avantageux de représenter par un tableau d'octets, ou de mots de 16 bits, ou de 32, ou de 64 etc.

                                  Laissons le choix à l'utilisateur,

                                  BoolArray<33, uint64_t>  mon_tableau;
                                  

                                  par un paramètre supplémentaire du template.

                                  Voila le lancement des

                                  test_brackets<uint8_t >("uint8_t");
                                  test_brackets<uint16_t>("uint16_t");
                                  test_brackets<uint32_t>("uint32_t");
                                  test_brackets<uint64_t>("uint64_t");

                                  qui affichent

                                  test 33 bits brackets avec éléments de type uint8_t, taille objet = 5 octets
                                  Bits à 1 : 1 6 32 
                                  test 33 bits brackets avec éléments de type uint16_t, taille objet = 6 octets
                                  Bits à 1 : 1 6 32 
                                  test 33 bits brackets avec éléments de type uint32_t, taille objet = 8 octets
                                  Bits à 1 : 1 6 32 
                                  test 33 bits brackets avec éléments de type uint64_t, taille objet = 8 octets
                                  Bits à 1 : 1 6 32 

                                  expl: pour représenter 33 bits sur des entiers 16 bits, il en faut au minimum 3, donc 3*2 = 6 octets.

                                  Le code du test (la même séquence, avec différents types)

                                  template <typename Element_Type = uint8_t>
                                  void test_brackets(const std::string & name)
                                  {
                                      std::cout << "test 33 bits brackets avec éléments de type " << name;
                                      BoolArray<33, Element_Type> a;
                                      std::cout << ", taille objet = " << sizeof(a) << " octets" << std::endl;
                                  
                                      a[0] = true;
                                      a[1] = true;
                                      a[5] = true;
                                      a[6] = true;
                                  
                                      a[0]  = false;
                                      a[32] = true;
                                      a[5]  = false;
                                  
                                      std::cout << "Bits à 1 : ";
                                      for (int i = 0; i < 33; i++) {
                                          if (a[i]) std::cout << i << " ";
                                      }
                                      std::cout << std::endl;
                                  
                                  }
                                  


                                  Et le code des classes

                                  template<int size, typename Element_Type>
                                  class BoolArrayPosition;
                                  
                                  template<int size, typename Element_Type = uint8_t>
                                  class BoolArray
                                  {
                                      constexpr static int BITS_BY_ELEMENT = 8 * sizeof(Element_Type);
                                      constexpr static Element_Type ONE = 1;
                                      Element_Type m_array[(size + BITS_BY_ELEMENT - 1)
                                                           / BITS_BY_ELEMENT] = {0};
                                  
                                  public:
                                  
                                      void set(unsigned int i)
                                      {
                                          m_array[i / BITS_BY_ELEMENT] |=  ONE << (i % BITS_BY_ELEMENT);
                                      }
                                  
                                      void reset(unsigned int i)
                                      {
                                          m_array[i / BITS_BY_ELEMENT] &= ~(ONE << (i % BITS_BY_ELEMENT));
                                      }
                                  
                                      void set(unsigned i, bool value)
                                      {
                                          if (value) {
                                              set(i);
                                          } else {
                                              reset(i);
                                          }
                                      }
                                  
                                      bool get(unsigned int i)
                                      {
                                          return m_array[i / BITS_BY_ELEMENT] &  (ONE << (i % BITS_BY_ELEMENT));  // conversion en bool
                                      }
                                  
                                      BoolArrayPosition<size, Element_Type> operator[](unsigned int i);
                                  };
                                  
                                  template<int size, typename Element_Type> class BoolArrayPosition
                                  {
                                      BoolArray<size, Element_Type> &m_array;
                                      unsigned m_i;
                                  public:
                                      BoolArrayPosition(BoolArray<size, Element_Type> &array, unsigned int i)
                                          : m_array{array}
                                          , m_i{i} {}
                                  
                                      bool operator=(bool value)
                                      {
                                          m_array.set(m_i, value);
                                          return value;
                                      }
                                  
                                      operator bool() const
                                      {
                                          return m_array.get(m_i);
                                      }
                                  
                                  };
                                  
                                  template<int size, typename Element_Type> 
                                  BoolArrayPosition<size, Element_Type> BoolArray<size, Element_Type>::operator[](unsigned int i)
                                  {
                                      return BoolArrayPosition<size, Element_Type> {*this, i};
                                  }
                                  
                                  template <typename Element_Type = uint8_t>
                                  void test_brackets(const std::string & name)
                                  {
                                      std::cout << "test 33 bits brackets avec éléments de type " << name;
                                      BoolArray<33, Element_Type> a;
                                      std::cout << ", taille objet = " << sizeof(a) << " octets" << std::endl;
                                  
                                      a[0] = true;
                                      a[1] = true;
                                      a[5] = true;
                                      a[6] = true;
                                  
                                      a[0]  = false;
                                      a[32] = true;
                                      a[5]  = false;
                                  
                                      std::cout << "Bits à 1 : ";
                                      for (int i = 0; i < 33; i++) {
                                          if (a[i]) std::cout << i << " ";
                                      }
                                      std::cout << std::endl;
                                  
                                  }

                                  Exercice amusant : Quand on programme on fait des erreurs, c'est pour ça qu'il faut tester. Au départ j'avais écrit

                                  void reset(unsigned int i)
                                      {
                                          m_array[i / BITS_BY_ELEMENT] &= ~(1 << (i % BITS_BY_ELEMENT));
                                      }

                                  et pareil pour set, et ça marchait pas pour uint64_t.

                                  Saurez-vous expliquer pourquoi ?

                                  ---

                                  Bref moralité, si on veut mémoriser 55 bits au maximum, on les met dans un entier 64 bits si y en a, et c'est réglé en 10 lignes.





                                  -
                                  Edité par michelbillaud 3 avril 2024 à 22:32:51

                                  • Partager sur Facebook
                                  • Partager sur Twitter

                                  tableau _Bool renvoit des entiers

                                  × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                                  • Editeur
                                  • Markdown