readme
构造函数是创建一个对象的第一步,它们负责开辟必要的内存空间和生成对象的各个成员变量。理论上讲不会有人优化性能的时候会想到优化构造函数,因为它们太普通了,甚至有的时候构造函数一行代码都没有。但实际上,构造函数的不同写法也是有区别的,下文举例说明。
构造函数简介
构造函数分两部分:参数初始化列表、函数体。对象的成员变量可以出现在这两部分代码中,这是显而易见的。本质上,即便成员变量没有出现,也会被创建出来。当一个成员变量需要在对象构造函数中被初始化时,有两种习惯写法:在参数初始化列表中、在函数体中。这篇博客的重点就是,如果在构造函数题中初始化成员变量,会额外执行一遍该变量的默认构造函数。
测试程序中有三个类:product_manager, zoo1, zoo2。zoo1和zoo2各自有一个product_manager类型的成员变量。但是zoo1和zoo2对成员变量的初始化方式不同,正确的做法是将初始化放在初始化列表中,因为必须要等成员变量初始化完成之后才会执行构造函数体。也就是说执行构造函数体时,成员变量已经被创建出来了,如果在函数体中初始化某个成员变量,相当于初始化某个成员变量之后立即马上给它赋一个新值,这是一种冗余。如果将成员变量的初始化放在初始化列表中,可以理解为给成员变量的构造函数一个参数,达到的目的是一样的,但是会有更好的效率,优化掉了一次默认构造过程。
测试程序
//common.h
#ifndef _COMMON_H_
#define _COMMON_H_
#include <string>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <iostream>
#include <utility>
#include <algorithm>
#include <vector>
#include <iterator>
#include <sys/time.h>
using namespace std;
#endif
//redundancy_construct.cpp
#include "common.h"
class product_manager
{
public:
product_manager();
product_manager(const string& other);
product_manager& operator=(const string& other);
~product_manager() {};
private:
string _skill;
};
product_manager::product_manager()
{
printf("in product_manager::product_manager()\n");
}
product_manager::product_manager(const string& skill)
{
printf("in product_manager:product_manager(const string& other)\n");
_skill = _skill;
}
product_manager& product_manager::operator=(const string& skill)
{
printf("in product_manager& product_manager::operator=(dconst string& skill)\n");
_skill = skill;
return *this;
}
class zoo1
{
public:
zoo1()
{
someone = "dropping waste";
}
private:
product_manager someone;
};
class zoo2
{
public:
zoo2():someone("eatting waste"){}
private:
product_manager someone;
};
int main(void)
{
printf("constructing zoo1\n");
zoo1 test_zoo1;
printf("constructing zoo2\n");
zoo2 test_zoo2;
return 0;
}
编译和执行结果
g++ -o redundancy_construct redundancy_construct.cpp -O0 -g -Wall -std=c++11
./redundancy_construct
constructing zoo1
in product_manager::product_manager()
in product_manager& product_manager::operator=(dconst string& skill)
constructing zoo2
in product_manager:product_manager(const string& other)