自动和动态变量规则在零初始化中的差异

发布于 2025-02-01 00:50:47 字数 599 浏览 3 评论 0原文

这样的代码,

#include <iostream>
 
class obj
{
public:
    int v;
};

int main(int argc, char *argv[])
{
    obj o1; 
    std::cout << o1.v << std::endl; // print 32766, indeterminate values
    obj *o2 = new obj();
    std::cout << o2->v << std::endl; // print 0,but why?

    int v1;
    std::cout << v1 << std::endl; // print 22024, indeterminate values
    int *v2 = new int;
    std::cout << *v2 << std::endl; // print 0,but why?
    return 0;
}

我知道全局或静态变量将被初始化。
自动做不确定的值。
但是堆对象使用新关键字,有任何引用来解释它吗?

code like this,

#include <iostream>
 
class obj
{
public:
    int v;
};

int main(int argc, char *argv[])
{
    obj o1; 
    std::cout << o1.v << std::endl; // print 32766, indeterminate values
    obj *o2 = new obj();
    std::cout << o2->v << std::endl; // print 0,but why?

    int v1;
    std::cout << v1 << std::endl; // print 22024, indeterminate values
    int *v2 = new int;
    std::cout << *v2 << std::endl; // print 0,but why?
    return 0;
}

I know the global or static variables will be initialize zero.
and automatic does the indeterminate values.
but the heap object use new keyword, has any reference to explain it?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

拥抱我好吗 2025-02-08 00:50:47

obj *o2 = new obj();值初始化这意味着该对象的初始化为零,因此数据成员v将被初始化为0

可以从值初始化

这是用空初始化器构造对象时执行的初始化。

  new T()(2)     
 

2,6)当由具有动态存储持续时间的对象由新表达式创建,其初始化器由一个空的括号或括号组成(因为C ++ 11);


另一方面,

int *v2 = new int; //this uses default initialization
std::cout << *v2 << std::endl; //this is undefined behavior

以上会导致不确定的行为,因为您正在提取v2,并且分配的int对象是非初学的,因此不确定价值。

不确定的行为意味着任何事情都可能发生。但是,永远不要依靠(或基于结论),该程序的输出具有UB。该程序可能只是崩溃。

默认初始化

这是当对象没有初始化器构造时执行的初始化。

 新的T(2)     
 

当没有初始化器的新表达式创建具有动态存储持续时间的对象时;

默认初始化的效果是:

  • 否则,没有进行初始化:具有自动存储持续时间(及其子对象)的对象包含不确定的值。

obj *o2 = new obj(); is value initialization meaning the object will be zero initialized and hence the data member v will be initialized to 0.

This can be seen from value initialization:

This is the initialization performed when an object is constructed with an empty initializer.

new T ()  (2)     

2,6) when an object with dynamic storage duration is created by a new-expression with the initializer consisting of an empty pair of parentheses or braces (since C++11);


On the other hand,

int *v2 = new int; //this uses default initialization
std::cout << *v2 << std::endl; //this is undefined behavior

the above leads to undefined behavior because you're dereferencing v2 and the allocated int object has is uninitialized and so has indeterminate value.

Undefined behavior means anything can happen. But never rely(or make conclusions based) on the output of a program that has UB. The program may just crash.

This can be seen from default initialization:

This is the initialization performed when an object is constructed with no initializer.

new T     (2)     

when an object with dynamic storage duration is created by a new-expression with no initializer;

The effects of default initialization are:

  • otherwise, no initialization is performed: the objects with automatic storage duration (and their subobjects) contain indeterminate values.
浅浅淡淡 2025-02-08 00:50:47

从C ++ 17标准(11.6个初始化器)

11一个对象,其初始化器是一组空括号,即
(),应进行价值限制。

对于基本类型,它意味着零限制。

因此,在此声明中,

obj *o2 = new obj();

动态分配的对象的数据成员v被零定位。

至于此代码段

int *v2 = new int;
std::cout << *v2 << std::endl; // print 0,but why?

,则未初始化指针v2指向的对象,下一个输出语句可以输出在分配新对象的内存范围内存储的任何值。

From the C++ 17 Standard (11.6 Initializers)

11 An object whose initializer is an empty set of parentheses, i.e.,
(), shall be value-initialized.

For fundamental types as int it means zero-initialization.

So in this declaration

obj *o2 = new obj();

the data member v of the of the dynamically allocated object is zero-initialized.

As for this code snippet

int *v2 = new int;
std::cout << *v2 << std::endl; // print 0,but why?

then the object pointed to by the pointer v2 is not initialized and the next output statement can output any value that was stored in the memory extent where the new object is allocated.

我很坚强 2025-02-08 00:50:47

初始化规则是一团糟。因此,让我们只是踩它们并强制问题:

class obj
{
public:
    int v{};
};

现在,v始终将被初始化。如果您添加一个不初始化v的构造函数,则可以有效,因为编译器会自动添加成员初始化。


至于为什么您的代码表现得如此之多:

obj o1; 
std::cout << o1.v << std::endl; // print 32766, indeterminate values

o1是在堆栈(或实际上是寄存器)上创建的,默认初始化。对于int,这意味着没有初始化。堆栈上(或寄存器中)上的任何随机数据都是您得到的。

obj *o2 = new obj();
std::cout << o2->v << std::endl; // print 0,but why?

从C ++ 17标准(11.6个初始化器):

11一个对象,其初始化器是一个空括号集,即((),应为价值。

值初始化 int将其设置为0。

int v1;
std::cout << v1 << std::endl; // print 22024, indeterminate values

默认初始化,您将获得随机数据。

int *v2 = new int;
std::cout << *v2 << std::endl; // print 0,but why?

默认初始化,您将获得随机数据。除非应用程序重复使用,否则新鲜分配的内存恰好是0。

Initialization rules are a mess to remember. So lets just side step them and force the issue:

class obj
{
public:
    int v{};
};

There, now v is always going to be initialized. That even works if you add a Constructor that doesn't initialize v as then the member initialization is added automatically by the compiler.


As for why your code behaved as it did:

obj o1; 
std::cout << o1.v << std::endl; // print 32766, indeterminate values

o1 is created on the stack (or actually a register) and default initialized. Which for the int means no initialization. Whatever random data is on the stack (or in the register) is what you get.

obj *o2 = new obj();
std::cout << o2->v << std::endl; // print 0,but why?

From the C++ 17 Standard (11.6 Initializers):

11 An object whose initializer is an empty set of parentheses, i.e., (), shall be value-initialized.

Value initialization of int sets it to 0.

int v1;
std::cout << v1 << std::endl; // print 22024, indeterminate values

Default initialization and you get random data.

int *v2 = new int;
std::cout << *v2 << std::endl; // print 0,but why?

Default initialization and you get random data. Freshly allocated memory just happens to be 0 unless it's reused by the application.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文