首页 > 编程语言 >深入解析C++中自动生成默认构造函数的五种情况

深入解析C++中自动生成默认构造函数的五种情况

时间:2024-06-09 11:32:16浏览次数:17  
标签:对象 成员 默认 编译器 五种 C++ 基类 构造函数

自动生成默认构造函数的情况以及相关解释

在 C++ 中,当一个类没有任何用户定义的构造函数时,编译器会自动为这个类生成一个默认构造函数。以下是具体情况的解释以及示例:

1. 带有默认构造函数的类成员对象

如果一个类没有任何构造函数,但它含有一个成员对象,而该成员对象有默认构造函数,那么编译器会为这个类合成一个默认构造函数。然而,这个合成操作只有在构造函数真正被需要(即,确实有对象创建动作)时才会发生。同时,这个类的构造函数必须按照成员对象在类中的声明顺序调用每个成员对象的默认构造函数。

#include <iostream>

class Member {
public:
    Member() {
        std::cout << "Member default constructor called" << std::endl;
    }
};

class MyClass {
public:
    Member member; // MyClass 自动生成默认构造函数, 调用 Member 的默认构造函数
};

int main() {
    MyClass obj; // 此处会自动生成并调用 MyClass 默认构造函数
    return 0;
}
2. 带有默认构造函数的基类

如果一个没有任何构造函数的派生类继承自一个有默认构造函数的基类,那么该派生类会合成一个构造函数,该构造函数调用基类的默认构造函数。

#include <iostream>

class Base {
public:
    Base() {
        std::cout << "Base default constructor called" << std::endl;
    }
};

class Derived : public Base {
    // 编译器为 Derived 合成一个默认构造函数,调用 Base 的默认构造函数
};

int main() {
    Derived obj; // 此处会自动生成并调用 Derived 默认构造函数,同时调用 Base 默认构造函数
    return 0;
}
3. 带有虚函数的类

如果一个类声明了至少一个虚函数,编译器会为这个类合成一个默认构造函数,即使没有其他构造函数。

#include <iostream>

class MyClass {
public:
    virtual void myFunction() { } // 声明虚函数
};

int main() {
    MyClass obj; // 此处会自动生成并调用 MyClass 默认构造函数
    return 0;
}
4. 带有虚基类的类

如果一个类继承自一个或多个虚基类,编译器会自动为这个类生成一个默认构造函数。

#include <iostream>

class Base {
public:
    Base() {
        std::cout << "Base default constructor called" << std::endl;
    }
};

class Derived : public virtual Base {
    // 编译器为 Derived 合成一个默认构造函数,调用 Base 的默认构造函数
};

int main() {
    Derived obj; // 此处会自动生成并调用 Derived 默认构造函数,同时调用 Base 默认构造函数
    return 0;
}
5. 合成的默认构造函数只初始化基类子对象和成员类对象

编译器合成的默认构造函数只会初始化基类子对象和成员类对象。所有其他的非静态数据成员都不会被初始化,它们将保留未定义的初始值。

#include <iostream>

class Member {
public:
    Member() {
        std::cout << "Member default constructor called" << std::endl;
    }
};

class MyClass {
public:
    int x;
    Member member; // MyClass 自动生成默认构造函数, 调用 Member 的默认构造函数
    
    void print() {
        std::cout << "x = " << x << std::endl; // x 是未初始化的,值是未定义的
    }
};

int main() {
    MyClass obj; // 此处会自动生成并调用 MyClass 默认构造函数
    obj.print(); // 打印未初始化的 x 的值
    return 0;
}

总结

自动生成默认构造函数的情况如下:

  1. 带有默认构造函数的类成员对象:类没有构造函数,但成员对象有默认构造函数。
  2. 带有默认构造函数的基类:派生类没有构造函数,但基类有默认构造函数。
  3. 带有虚函数的类
  4. 带有虚基类的类
  5. 合成的默认构造函数仅初始化基类子对象和成员类对象:而未初始化的非静态数据成员具有未定义的值。

这些情况确保了类在实例化时能够正确初始化其成员和基类,即使用户未显式定义构造函数。

标签:对象,成员,默认,编译器,五种,C++,基类,构造函数
From: https://blog.csdn.net/m0_72877724/article/details/139548907

相关文章

  • 为什么C++友元函数必须在类内部声明?解析与案例
    友元函数是C++中独特的编程结构,允许一个非成员函数或者其他类访问另一个类的私有和保护数据成员。友元在很多情况下是非常有用的,比如操作符重载、类间紧密合作等。为什么需要在类内部声明友元函数?访问权限:友元函数需要访问类的私有和保护数据成员。为此,必须在类内部声明,以便......
  • 栈经典题目(C++)
    文章目录前言一、删除字符串中的所有相邻重复项1.题目解析2.算法原理3.代码编写二、基本计算器II1.题目解析2.算法原理3.代码编写三、字符串解码1.题目解析2.算法原理3.代码编写四、验证栈序列1.题目解析2.算法原理3.代码编写总结前言一、删除字符串中的所有......
  • 【四种语言一网打尽(C\C++\Python\Golang)】L1-005 考试座位号
    L1-005考试座位号每个PAT考生在参加考试时都会被分配两个座位号,一个是试机座位,一个是考试座位。正常情况下,考生在入场时先得到试机座位号码,入座进入试机状态后,系统会显示该考生的考试座位号码,考试时考生需要换到考试座位就座。但有些考生迟到了,试机已经结束,他们只能拿着......
  • C++ 对拍
    准备timeb毫秒级随机数文件这里以P1001A+BProblem为例。std.cpp-std.exe(std.lnk)#include<bits/stdc++.h>usingnamespacestd;signedmain(){intx,y;cin>>x>>y;cout<<x+y<<endl;return0;}force.cpp-force.exe#......
  • vscode编译c/c++找不到jni.h文件
    解决办法:一、下载JDK访问Oracle官网的Java下载页面:JavaDownloads|Oracle选择适合您操作系统的JDK版本:对于Windows,选择“Windowsx64”或“Windowsx86”(取决于您的系统是64位还是32位)。对于Linux,选择适合您Linux发行版的压缩包。对于Mac,选择“.dmg”或“.pkg”安装......
  • 【C++/STL】list(常见接口、模拟实现、反向迭代器)
     ......
  • C++ OpenCV 图像分类魔法:探索神奇的模型与代码
    ⭐️我叫忆_恒心,一名喜欢书写博客的研究生......
  • C++20协程接口说明
    等待体的接口说明: boolawait_ready()表达了等待体对象是否准备就绪,返回false表示没有准备好,返回true表示准备好了,这个返回值决定了等待体的执行流程。 boolawait_suspend(Coro::coroutine_handle<Task::promise_type>)当await_ready返回fasle时,进入此函数执行,如果await_r......
  • 柔性数组+总结C/C++中程序内存区域划分
    柔性数组一.柔性数组1.柔性数组的定义2.柔性数组的特点3.柔性数组的使用4.柔性数组的优势二.总结C/C++中程序内存区域划分前言:也许你从来没有听说过柔性数组这个概念,但是它确实是存在的。一.柔性数组1.柔性数组的定义C99中,结构体中的最后一个元素允许是未知大小的......
  • C++特点,对象的概念,初始化和赋值
    C++是面向对象的变成语言,C++的特点是封装,继承,多态,同时也是面向对象语言的特点。在C++中的对象指一块能存储数据并具有某种类型的内存空间,例如当我们写一句inta时,int是C++的基本类型,a就是一个对象,如果将inta写成的inta=10;那么这句语句的含义是创建了一个int类型的对象,并给......