Take an ordinary struct (or class) with Plain Old Data types and objects as members. Note that there is no default constructor defined.
struct Foo
{
int x;
int y;
double z;
string str;
};
Now if I declare an instance f on the stack and attempt to print its contents:
{
Foo f;
std::cout << f.x << " " << f.y << " " << f.z << f.str << std::endl;
}
The result is garbage data printed for x, y, and z. And the string is default initialized to be empty. As expected.
If I create an instance of a shared_ptr<Foo>
using make_shared
and print:
{
shared_ptr<Foo> spFoo = make_shared<Foo>();
cout << spFoo->x << " " << spFoo->y << " " << spFoo->z << spFoo->str << endl;
}
Then, x, y, and z are all 0
. Which makes it appear that shared_ptr
performs a default initialization (zero init) on each member after the object instance is constructed. At least that's what I observe with Visual Studio's compiler.
Is this standard for C++? Or would it be necessary to have an explicit constructor or explicit ={}
statement after instantiation to guarantee zero-init behavior across all compilers?
If T is scalar (arithmetic, pointer, enum), it is initialized from 0 ; if it's a class type, all base classes and data members are zero-initialized; if it's an array, each element is zero-initialized.
Description. It constructs an object of type T passing args to its constructor, and returns an object of type shared_ptr that owns and stores a pointer to it.
The difference is that std::make_shared performs one heap-allocation, whereas calling the std::shared_ptr constructor performs two.
One reason is because make_shared allocates the reference count together with the object to be managed in the same block of memory.
If you see e.g. this std::make_shared
reference you will see that
The object is constructed as if by the expression
::new (pv) T(std::forward<Args>(args)...)
, wherepv
is an internalvoid*
pointer to storage suitable to hold an object of typeT
.
That means std::make_shared<Foo>()
basically does new Foo()
. That is, it value initializes the structure which leads to the zeroing of the non-class member variables.
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