Home > Mobile >  std::map object destructor getting called?
std::map object destructor getting called?

Time:06-21

I have a global map object which contains an ID and a class object, but I don't understand why the destructor for the objects in the map are getting called.

#include <map>
#include <iostream>
#include <cassert>
#include <chrono>
#include <thread>
class TestMapObject{

private:
    std::string m_sName;
public:
    TestMapObject(const std::string& sName){
        std::cout << "Constructor called" << std::endl;
        m_sName = sName;
    }
    ~TestMapObject(){
        std::cout << "Destructor called" << std::endl;
    }
    const std::string& GetName(){
        return m_sName;
    }
};

namespace Test{

    enum ETestMapKeyId{
      k_ETestMapKeyNone = 0,
        k_ETestMapKeyFirst,
        k_ETestMapKeySecond,
    };

    std::map<ETestMapKeyId, TestMapObject> g_tMap;

    TestMapObject* GetMapObjectById(ETestMapKeyId eID){
        auto itFound = g_tMap.find(eID);
        
        assert(itFound != g_tMap.end());
        
        return &itFound->second;
    }
}



int main(){
    Test::g_tMap.insert(std::pair<Test::ETestMapKeyId,TestMapObject>(Test::k_ETestMapKeyFirst,TestMapObject("Alice")));
    Test::g_tMap.insert(std::pair<Test::ETestMapKeyId,TestMapObject>(Test::k_ETestMapKeySecond,TestMapObject("Mocha")));
    //destructor gets called here
    std::cout << " are we destructed? " << std::endl;
    
    TestMapObject* tmKeyFirst = Test::GetMapObjectById(Test::k_ETestMapKeyFirst);
    TestMapObject* tmKeySecond = Test::GetMapObjectById(Test::k_ETestMapKeySecond);
    
    
    
    for(;;){
        std::this_thread::sleep_for (std::chrono::seconds(1));
        std::cout << tmKeyFirst->GetName() << std::endl ;
        std::cout << tmKeySecond->GetName() << std::endl ;
    }
    return 0;
}

I'm able to retrieve a pointer to the objects with GetMapObjectById and continuously able to print their name (Which might be undefined behavior considering their destructor was called). But I'm unsure why the destructor gets called before the application ends..

Output

Constructor called
Destructor called
Destructor called
Constructor called
Destructor called
Destructor called
 are we destructed? 

---continues loop print
Alice
Mocha

CodePudding user response:

What you see is not the std::map getting destroyed, but the temporaries you are using to insert elements in the map. You can use emplace to avoid the construction (and destruction) of that temporaries:

Test::g_tMap.emplace(Test::k_ETestMapKeyFirst,"Alice");
Test::g_tMap.emplace(Test::k_ETestMapKeySecond,"Mocha");

Live Demo

  •  Tags:  
  • c
  • Related