zoukankan      html  css  js  c++  java
  • c++11 委派构造函数

    委派构造函数可以减少构造函数的书写量:

    class Info {
    public:
     Info() : type(1), name('a') {
      InitRest();
     }
    
     Info(int i) : type(i), name('a') {
      InitRest();
     }
    
     Info(char e) : type(1),, name(e) {
      InitRest();
     }
    
    private:
     void InitRest() { //其他初始化 }
     int type;
     char name;
    };

    每个构造函数都需要初始化列表来初始化成员type和name,且都调用了相同的函数InitRest,存在重复。

    而在C++11中,可以使用委派构造函数来简化代码,如下:

    class Info {
    public:
     Info() { InitRest(); }  //称为目标构造函数(被调用)
     Info(int i) : Info() { type = i; }  //委派构造函数(调用者)
     Info(char e) : Info() { name = e; }
    
    private:
     void InitRest() { // other int }
     int type {1};
     char name {'a'};  
    };

    委派构造函数只能在函数体内为type,name等成员赋值,因为委派构造函数不能有初始化列表。C++中,构造函数不能同时使用委派和初始化列表。

    初始化列表的初始化总是先于构造函数完成,作一下修改:

    class Info {
    public:
     Info() : Info(1, 'a') {}
     Info(int i) : Info(i, 'a') {}
     Info(char e) : Info(1, e) {}
    
    private:
     Info(int i, char e) : type(i), name(e) {} //将初始化动作放在一个通用的构造函数里
     int type;
     char name; 
    };

    在构造函数比较多时,可以有不止一个委派构造函数,目标函数也可以是委派构造函数,可以在委派构造函数中形成链状的委派构造关系。

    class Info {
    public:
     Info() : Info(1) {}
     Info(int i) : Info(i, 'a') {}  //可以委派成链状,但不能形成环。
     Info(char e) : Info(1, e) {}
    
    private:
     Info(int i, char e) : type(i), name(e) {}
     int type;
     char name;
    };

    委派构造函数的应用:

    1.模板:

    #include <list>
    #include <vector>
    #include <deque>
    
    using namespace std;
    
    class TDConstructed {
     template<class T>
     TDConstructed(T first, T last) : l(first, last) {}
    
     list<int> l;
    
    public:
     TDConstructed(vector<short> & v) : TDConstructed(v.begin(), v.end()) {}
     TDConstructed(deque<int> & d) : TDConstructed(d.begin(), d.end()) {}
    }

    以上定义了一个构造函数模板,通过两个委派构造函数的委托,构造函数模板被实例化。

    2. 异常处理:

    #include <iostream>
    using namespace std;
    
    class DCExcept(double d) try : DCExcept(1, d) {
       cout << "Run the body." << endl;   
    } catch(...) {
      cout << "caught exception." << endl;
    }
    
    private:
     DCExcept(int i, double d) {
       cout << "going to throw!" << endl;
       throw 0;
     }
    
     int type;
     double data;
    };
    
    int main() {
     DCExcept a(1.2);
    }

    目标函数中抛出异常,可以在委派构造函数中捕获。

  • 相关阅读:
    C#多线程学习笔记(三)——线程池
    html解析工具
    怎么样获取手机的主题
    我改进的《豆瓣搜》前后对比及源代码
    【收藏】Silverlight Style (二) 自定义样式在后台代码中应用
    C#多线程学习笔记(一)
    学习Linux——学习正确的思考方式(转)
    电信禁路由上网的破解方法
    印度软件业
    中国与印度软件工程师之比较
  • 原文地址:https://www.cnblogs.com/sssblog/p/10203026.html
Copyright © 2011-2022 走看看