Search code examples
c++testingcontainerspushmemory-address

insert an element into container without changing its original adress in C++


I have 2 classes. The class Covid has a list of Deviant. I need to add an Deviant to the list .

class Deviant : public Individu{
    public:
        Deviant();
        Deviant(const Personne& );
        Deviant(const Personne&, const std::string& );
        ~Deviant();
        const std::string& getObs() const;
        void setObs(const std::string&);
    std::vector<Personne> p;
    std::string obs;

};
class Covid{
    public:
        Covid();
        ~Covid();
        void push(const Deviant&);
        const Deviant& top() const;
    std::list<Deviant > d;
};

I need to implement methods push() that pushes a Deviant into list d and top() that returns the first element in the list d. I need to pass this test

TEST_CASE("COVID") {
  Deviant  zz[] = { Deviant(Personne("bruno") , "19980930"), 
                    Deviant(Personne("alexis"), "20160930"), 
                    Deviant(Personne("loic")  , "19990930"), 
                    Deviant(Personne("jeremy"), "20210930") 
                   };

  Covid c;
  for (int i=0; i< 4; ++i)
     c.push(zz[i]);
  std::cout << c.top().getObs() << std::endl;
  std::cout << zz[3].getObs() << std::endl;
   CHECK(&c.top() == &zz[3]);
   /*c.pop();
   CHECK(&c.top() == &zz[1]);
   c.pop();
   CHECK(&c.top() == &zz[2]);
   c.pop();
   CHECK(&c.top() == &zz[0]);*/
}

but the first check does pass

tests.cpp:225: FAILED:
  CHECK( &c.top() == &zz[3] )
with expansion:
  0x000055bded197be0 == 0x00007fffad1896a8

what is the best container to store objects without changing their original addresses ?


Solution

  • Your test will always fail, because std::list makes a copy of whatever is pushed into it. You are testing the copy's address against the original's address, which will never match. The only way to push an object into a container without copying/moving it is to push a pointer to the object instead. IOW, use std::list<Deviant*> and c.push(&zz[i]);, and then adjust top() and your tests accordingly, eg:

    class Covid{
        public:
            Covid();
            ~Covid();
            void push(Deviant*);
            const Deviant* top() const;
        std::list<Deviant*> d;
    };
    
    TEST_CASE("COVID") {
      Deviant  zz[] = { Deviant(Personne("bruno") , "19980930"), 
                        Deviant(Personne("alexis"), "20160930"), 
                        Deviant(Personne("loic")  , "19990930"), 
                        Deviant(Personne("jeremy"), "20210930") 
                       };
    
      Covid c;
      for (int i=0; i< 4; ++i)
         c.push(&zz[i]);
      std::cout << c.top()->getObs() << std::endl;
      std::cout << zz[3].getObs() << std::endl;
       CHECK(c.top() == &zz[3]);
       /*c.pop();
       CHECK(c.top() == &zz[1]);
       c.pop();
       CHECK(c.top() == &zz[2]);
       c.pop();
       CHECK(c.top() == &zz[0]);*/
    }