For example, when we want to create a std::pair, we can simply call:
std::make_pair(5, "foo");
But when we intend to create a shared_ptr, we have to provide type info:
std::make_shared<Foo>("Boo", 1024);
Is there any reason that makes them different?
std::make_sharedAllocates and constructs an object of type T passing args to its constructor, and returns an object of type shared_ptr<T> that owns and stores a pointer to it (with a use count of 1). This function uses ::new to allocate storage for the object.
So, if you throw exception from your class' constructor, then std::make_shared will throw it too. Besides exceptions thrown from constructor, std::make_shared could throw std::bad_alloc exception on its own.
Its seesm straight-forward -- make_shared needs to copy/move the unnamed MyClass() temp you created explicitly into the shared object space it allocates. It uses the move constructor if it can, or the copy constructor if there is no move constructor. What do you expect to happen?
The function std::make_pair<T1, T2>
creates a pair std::pair<T1, T2>
where the types T1
and T2
are the types of arguments of the function. As such they can be deduced by the compiler and normally you do not need to provide them explicitly.
The function std::make_shared<T>
creates a new object of type T
and returns shared_ptr<T>
storing this object. The function passes all its arguments to the constructor of T
. There is no way for the compiler to deduce the type T
from the arguments. Even if the argument is e.g. const T&
the compiler cannot know if you want to create shared_ptr<T>
or shared_ptr<SomeOtherTypeWithConstructorAcceptingT>
.
std::make_shared
should be called emplace_shared
-- it calls an arbitrary ctor.
make_pair
constructs a copy or move of its types.
They have different purposes: one is for type deduction help, the other for emplace construction. They are both factories, hence the make name.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With