来自C ++中的思考
构造函数的第一个隐藏参数是this指针。该指针保存调用者对象的地址。在构造函数的情况下,该指针指向未初始化的内存块。 构造函数的工作是正确初始化此内存块。
所以,基本上,构造函数用于获取指向RAM中对象空间的指针?那是对的吗?
默认构造函数如何初始化该内存?它被初始化为零吗?
答案 0 :(得分:2)
默认构造函数的作用与任何其他构造函数相同:初始化对象。默认构造函数(或只带有默认参数的构造函数)将成员变量设置为已知状态,如设置指向nullptr
(或0
)等的指针。
让我们说我们有这样的结构:
struct Foo
{
int a;
int* b;
// Default constructor
// Set `a` to `1`, and `b` to `nullptr`
Foo() : a(1), b(nullptr) {}
};
现在,当您声明Foo
类的实例时,您知道成员变量将具有什么状态。如果没有构造函数,Foo
类的普通局部变量实例将具有a
和b
成员的未定义值。
如果您根本不提供构造函数,默认或其他,那么编译器将为您创建一个默认构造函数(需要一个,或者您将无法创建类的实例),但它将不要对成员进行任何初始化。
所讨论的隐藏参数是被称为this
的变量,它存在于所有不是static
的成员函数中。
答案 1 :(得分:2)
所以,基本上,构造函数用于获取指向RAM中对象空间的指针?这是对的吗?
不,构造函数不用于获取指针。
构造函数的目的是在创建此类的对象时初始化所有成员变量。它初始化内存中的对象。
默认构造函数是可以不带参数调用的构造函数。
实现类时,可以实现自己的默认构造函数,使其按照您的意愿执行。
如果没有为类提供任何构造函数,编译器将为此类提供默认构造函数,但不会初始化成员。
默认构造函数很重要,因为它们在某些情况下会自动调用:
- 当声明一个没有参数列表的对象值时,例如MyClass x ;;或动态分配,不带参数列表,例如,新的MyClass或新的MyClass();默认构造函数用于初始化对象
- 当声明一个对象数组时,例如
MyClass x[10];
或动态分配,例如new MyClass [10];
默认构造函数用于初始化所有元素- 当派生类构造函数未在其初始化列表中显式调用基类构造函数时,将调用基类的默认构造函数
- 当类构造函数没有在其初始化列表中显式调用其某个对象值字段的构造函数时,该字段类的默认构造函数被称为
- 在标准库中,当未明确给出值时,某些容器使用默认构造函数“填充”值,例如
vector<MyClass>(10);
使用10个元素初始化向量,这些元素使用我们类型的默认构造值填充。在上述情况下,如果该类没有默认构造函数,则会出错。
答案 2 :(得分:1)
没有。构造函数不用于获取指针。构造函数接收此指针。
构造函数用于初始化RAM中的对象空间。
默认构造函数执行您希望它执行的操作!我的意思是你可以为你的类编写自己的默认构造函数。这个默认构造函数可以初始化内存,或者根据你的选择保持未初始化。
同样,编译器会自动编写隐式默认构造函数来初始化对象RAM空间。它将负责初始化具有默认构造函数的类的非静态成员变量。例如,如果您的类具有非静态std::string
作为成员变量,那么将调用std::string
默认构造函数来初始化此变量。 POD
类型(int
,char
,指针,...)的所有非静态成员变量都不会被初始化。
答案 3 :(得分:0)
没有
MyClass obj; // Default construct
MyClass* obj2 = new MyClass; // Also default construct
在第一个中,首先分配obj
的空间,通常在堆栈中。第二个在堆上分配。它们所在的地址是在这种情况下传递给适当构造函数的地址。
第一个参数是 - { - 1}} - 指针情况不仅适用于默认构造函数,因为隐藏的this
指针作为第一个传递给所有非静态类方法参数 [1]
然后你可能知道其余的。构造函数设置并初始化对象的成员和状态以及需要完成的任何其他事情。
[1] 您是否观察过这样的例子?
this
这表明第一个参数是指向某个对象的指针绑定到my_type obj;
func_that_calls_a_callback(std::bind(&my_type::method, &obj));
的第一个参数。这成为my_type::method
指针,在这种情况下指向this
。
答案 4 :(得分:0)
所以,基本上,构造函数用于获取指向RAM中对象空间的指针?这是对的吗?
不,这只是一个后果
默认构造函数如何初始化该内存?它是否被初始化为零?“
否:默认构造函数只是一个函数。它会按照您的定义执行操作。 它通常被设计为通过为包含的变量(对象成员)分配适当的值或者通过调用它们自己的构造函数来“初始化”内存。
想一想:
class point
{
public:
int x,y; //< just two values
point() //< default constructor
{ x=0; y=0; } //< function body assigning values
};
或
class point
{
public:
int x,y; //< just two values
point() //< default constructor
:x(), y() //< member init-list explicitly calling contrutors
{} //< empty body
};
请注意,在您不声明point
类型的变量之前,不会执行任何操作。
int main()
{
point p; //< p created and point::point() called using p as *this
p.x=5; //< x member of p changed
return 0; //just exit main (jumps to the closing } )
} //< p destructor called here, using p as *this.
根据“隐式默认构造函数”,它的作用是:
对于所有基于类的类型,实际上删除默认ctor会替换隐式类型,但是 - 对于“内置类型”(如int,char,float等) - 默认显式 constructor -in fact-将值设置为零,但隐式不会执行任何操作,从而使值未初始化。 (实现可以使用不同的技术来得到相同的结果)