C++新手很容易陷入两个认识上的误区:

1.任何类如果不显示的定义一个构造函数那么编译器就会构造出一个默认构造函数。

2.默认构造函数负责类的所有数据成员的初始化,显然不是这样的。

为什么不是这样的,下面来进行详细的说明和解答,下面会说明在什么情况下一种有用的构造函数会被编译器构造出来。

类的默认构造函数:default construct,一个c++类什么时候需要构造出一个默认的构造函数,答案是在编译器需要的时候,这里指的是编译器需要的时候,举个例子。

Class Foo

{

Public :

Foo * pNext;

char * str;

}

在这个例子里面对象成员的初始化不应该交给编译器来做,因为对于类的对象的初始化是程序需要考虑的事情,当然也需要交由Foo类的构造者来完成。比如

Foo :: Foo()

{

Str = 0;

pNext =NULL;

}

  1. 默认构造函数由编译器声明分为多种的情形,其中情形一位:当一个类之中含有了一个已经存在默认构造函数其他类的对象时,那么这个类就需要声明出默认的构造函数来完成类的成员对象的初始化。

Class Foo

{

Public :

Foo ();

Foo(int);

}

Class Bar

{

Public :

Foo foo;

Char * str;

}

此时就需要类的构造函数来进行Foo类对象的初始化,这里再次分为两种情况,第一种就是Bar类的构造着不进行显示的构造函数编写,那么就会由编译器来进行默认构造函数的构建就像下面这样,编译器默认的构造函数只负责foo对象的初始胡他并不会负责str的初始化。

Bar::bar()

{

Foo.Foo::Foo();

}

当Bar类的构造着显示的声明了一个构造函数的时候编译器在用户代码之前也会负责进行Foo对象的初始化就像下面一样。

用户代码:Bar::bar()

{

Str = 0;

}

编译器添加了初始化代码之后的结构:

Bar::bar()

{

//在用户代码之前编译器必须负责构造foo对象

// Foo.Foo::Foo();

Str = 0;

}

需要注意的是当一个类包含了多个其他类的成员对象的时候需要按照顺序进行类的对象初始化向下面的例子。

Class point {public : point()}

Class line  {public: line(); line(int)}

Class shape {public: shape()……}

Class test

{

Public :

Point m_point;

Line m_line;

Shape m_shape;

Private :

Int m_ival;

}

显示的构造函数,用户代码:test::test():line(1024)

{

M_ival = 0;

}

编译器代码:

Test:test():line(1024)

{

//首先需要对对象point和shape进行初始化,这些操作都将由编译器完成

//Point:point::point();

Line:line::line(1024);

//Shape.shape::shape();

M_ival = 0;

}

2.带有默认构造函数的基类

带有默认构造函数的基类,对于这种类型的构造函数和之前提到过的相似,因为派生类对象在构造之前必须要先构造出基类的构造函数,所以编译器在编译阶段会进行代码扩展,将基类的默认构造函数添加到派生类的构造函数代码中。

3.基类含有vritual function 的派生类对象

因为这种类型的类编译器在编译阶段需要产生一个虚表vtab和一个指向vtab的虚表指针vptr,vptr内含虚表的地址值。出于这种考虑如果用户不声明一个构造函数,那么编译器必须合成出一个默认的构造函数来进行每一个对象的虚表指针vptr的初始化。

4.含有virtual class 的派生类

和上面的道理一样,编译器也必须产生出一个指向虚基类的指针进行虚基类成员的操作,这个阶段就发生在默认构造函数中。

隐藏在default construct后面的是什么的更多相关文章

  1. Spring Boot使用RestTemplate消费REST服务的几个问题记录

    我们可以通过Spring Boot快速开发REST接口,同时也可能需要在实现接口的过程中,通过Spring Boot调用内外部REST接口完成业务逻辑. 在Spring Boot中,调用REST Ap ...

  2. 【图片识别】java 图片文字识别 ocr (转)

    http://www.cnblogs.com/inkflower/p/6642264.html 最近在开发的时候需要识别图片中的一些文字,网上找了相关资料之后,发现google有一个离线的工具,以下为 ...

  3. java 图片文字识别 ocr

    最近在开发的时候需要识别图片中的一些文字,网上找了相关资料之后,发现google有一个离线的工具,以下为java使用的demo 在此之前,使用这个工具需要在本地安装OCR工具: 下面一个是一定要安装的 ...

  4. RestTemplate 使用中的几个问题

    Spring Boot使用RestTemplate消费REST服务的几个问题记录 我们可以通过Spring Boot快速开发REST接口,同时也可能需要在实现接口的过程中,通过Spring Boot调 ...

  5. Jackson学习笔记

    老版本的Jackson使用的包名为org.codehaus.jackson,而新版本使用的是com.fasterxml.jackson. Jackson主要包含了3个模块: jackson-core ...

  6. ASP.NET空网页生成默认代码注释

    当在Visual Studio下生成ASP.NET空网页时,默认生成代码: <%@ Page Language="C#" AutoEventWireup="true ...

  7. bootstrap加深

    1.安装: bootstrap中文网:http://www.bootcss.com/ bootstrap.css样式:http://v3.bootcss.com/css/#tables class=' ...

  8. lua 中的面向对象

    lua 是一种脚步语言,语言本身并不具备面向对象的特性. 但是我们依然可以利用语言的特性,模拟出面向对象的特性. 面向对象的特性通常会具备:封装,继承,多态的特性,如何在lua中实现这些特性,最主要的 ...

  9. Linux操作系统奥秘02-系统引导(GRUB)

    GRUB的加载流程 GRUB是GNU的一款多重引导软件.GRUB包含了3个重要的文件:stage1 ,e2fsstage1_5,stage2.这三个文件分别代表了GRUB运行的3个阶段. 1.stag ...

随机推荐

  1. Mac环境下PHPstorm配置xdebug开发调试web程序

    一.安装PHP的xdebug扩展 安装xdebug(技巧,为了找到适配的版本,让xdebug网站根据phpinfo()函数输出分析找到对应的方法及安装步骤:如果安装了多个PHP版本的话,尽量用phpi ...

  2. 轻量级封装DbUtils&Mybatis之三MyBatis分页

    MyBatis假分页 参考DefaultResultSetHandler的skipRows方法. 温馨提示:部分代码请参考轻量级封装DbUtils&Mybatis之一概要 解决方案 1)之前公 ...

  3. 导入和导出eclipse代码格式化模板

    导入和导出eclipse代码格式化模板 导出格式化代码模板:

  4. TCP三次握手和四次挥手、HTTP协议

    TCP三次握手和四次挥手 首先我们知道HTTP协议通常承载于TCP协议之上,HTTPS承载于TLS或SSL协议层之上 通过上面这张图我们能够知道.     在Http工作之前,Web浏览器通过网络和W ...

  5. linux oracle服务器无密码登录dba

    1.su - oracle 切换到oracle 2.sqlplus sys/manger as sysdba 3.新建用户: create user username identified by pa ...

  6. netcore中使用log4net日志

    第一.控制台程序中使用log4net  static void Main(string[] args) { ILoggerRepository repository = LoggerManager.C ...

  7. CC1,IceBreak,Hello world ,hello toastmaster

    this is my first speech:icebreak in toastmaster,it is precious memory for me,this is first time that ...

  8. Julia - 匿名函数

    Julia 中的函数可以被匿名构造,成为匿名函数,匿名函数是没有函数名的函数 julia> x -> x + 1 #3 (generic function with 1 method) 这 ...

  9. linux中的常用压缩与解压缩命令

    linux中常用的压缩格式有   .zip   .gz   .bz2   .tar.gz   .tar.bz2 一..zip 1.命令格式 zip 压缩文件名 源文件名         (压缩文件到当 ...

  10. Android屏幕相关概念和适配方法

    参考文档: 1.http://blog.csdn.net/carson_ho/article/details/51234308(略有修改) 2.http://www.cnblogs.com/cheng ...