c++smart-pointers

Shared pointer from static function


I am trying to improve my coding by using smart pointers, and am currently trying to replace all old raw pointers in our legacy code-base at work with smart pointers (std::unique_ptr & std::shared_ptr). I now have a case where a pointer is returned from a static function.

What will happen if I change this to a std::shared_ptr that will be created using std::make_shared and returned from the function?

Will the ref-count be able to reach 0 since one reference is stored inside the static function, or will it remain until the program exits?

Previous:

static MyObject* MyClass::createPointer()
{
    return new MyObject();
}

Now:

static std::shared_ptr<MyObject> MyClass::createSharedPointer()
{
    return std::make_shared<MyObject>();
}

Solution

  • Don't worry. Modern C++ compiler will do copy elision following your code pattern. It doesn't matter if it is a static function or not.

    But for std::shared_ptr, it's required to assign it to something or ref-count will be 0 (destructing the object immediately).

    #include <memory>
    #include <iostream>
    struct MyObject
    {
        MyObject(int i):member{i}{
    
        }
        ~MyObject(){
            std::cout << "MyObject#" << member << " destruct\n";
        }
    
        static std::shared_ptr<MyObject> createPointer(int i){
            return std::make_shared<MyObject>(i);
        }
        int member = 0;
    
       
    };
    
    static std::shared_ptr<MyObject> get_singleton_ptr(){
        static auto ptr = std::make_shared<MyObject>(3);
        return ptr;
    }
    
    MyObject& get_singleton_ref(){
        static auto ptr = std::make_unique<MyObject>(4);
        return *ptr;
    }
    
    int main() {
        MyObject::createPointer(1);
    
        auto ptr = MyObject::createPointer(2);
    
        get_singleton_ptr();
    
        get_singleton_ref();
    
        std::cout << "end program/scope\n";
    }
    

    The result should be

    MyObject#1 destruct
    end program/scope
    MyObject#2 destruct
    MyObject#4 destruct
    MyObject#3 destruct