c++ 11新特性总结_c++11新特性(三)

对于类

3.1 构造函数

3.1.1 控制构造函数

1.default 关键字生成默认构造函数和析构函数

default的默认构造方式可生成:默认无参数的构造函数,拷贝构造函数,赋值构造函数,析构函数同样可以由default默认构造

2.delete关键字 禁止拷贝构造 禁止赋值构造 禁止 自定义参数的构造函数 注意析构函数 不可由delete修饰

c++11以前的方式 是把需要禁止的构造函数 放在private里使外部无法调用

c++11风格的禁止构造的noncopyable基类实现如下 禁止了拷贝构造和赋值构造

class noncopyable{protected:constexpr noncopyable() = default;~noncopyable() = default;noncopyable(const noncopyable&) = delete;noncopyable& operator=(const noncopyable&) = delete;};

3.2 委托构造函数

一个构造函数,使用自己的参数,传递给其他构造函数去构造,作为自己的构造函数实现,

如下面的例子,后面两个构造函数 均传递参数 委托给第一个构造函数去实现

struct A {bool a_;char b_;int c_;float d_;double e_;A(bool a, char b, int c, float d, double e) : a_(a), b_(b), c_(c), d_(d), e_(e) {}//construct reuseA(int c) : A(true, 'b', c, 1.1, 1000.1) {}A(double e) : A(false, 'a', 0, 0.1, e) {}};int main(){A o1(10);std::cout << "a: " << o1.a_ << ", b: " << o1.b_ << ", c: " << o1.c_ << ", d: " << o1.d_ << ", e: " << o1.e_ << std::endl;A o2(5.5);std::cout << "a: " << o2.a_ << ", b: " << o2.b_ << ", c: " << o2.c_ << ", d: " << o2.d_ << ", e: " << o2.e_;getchar();return 0;}

3.3、移动构造函数:

std::move函数可以以非常简单的方式将左值引用转换为右值引用。C++ 标准库使用比如vector::push_back 等这类函数时,会对参数的对象进行复制,连数据也会复制.这就会造成对象内存的额外创建, 本来原意是想把参数push_back进去就行了,通过std::move,可以避免不必要的拷贝操作。

std::move是将对象的状态或者所有权从一个对象转移到另一个对象,只是转移,没有内存的搬迁或者内存拷贝所以可以提高利用效率,改善性能.。

对指针类型的标准库对象并不需要这么做

#include #include #include #include int main(){std::string str = "Hello";std::vector<:string> v;//调用常规的拷贝构造函数,新建字符数组,拷贝数据v.push_back(str);std::cout << "After copy, str is "" << str << """;//调用移动构造函数,掏空str,掏空后,最好不要使用strv.push_back(std::move(str));std::cout << "After move, str is "" << str << """;std::cout << "The contents of the vector are "" << v[0]<< "", "" << v[1] << """;getchar();return 0;}

3.4、override和final

作用于虚函数,更多的作用是:显式的标识是否应该多态继承或不应该。

继承:子类的虚函数多态实现要加override显式的表明,不让子类多态实现的虚函数也要记得加入final;

1、override:子类用override修饰其虚函数,表示要多态继承基类的虚函数。不可以修饰非虚函数

举一个rocksdb的merge运算符重载的例子:

class ProcessMerge : public rocksdb::MergeOperator {public:    virtual bool FullMergeV2 (const MergeOperationInput &merge_in,                              MergeOperationOutput *merge_out) const override {        merge_out->new_value.clear();        if (merge_in.existing_value != nullptr) {            merge_out->new_value.assign(merge_in.existing_value->data(), merge_in.existing_value->size());        }         for (const rocksdb::Slice& m : merge_in.operand_list) {            merge_out->new_value.append("|");            merge_out->new_value.append(m.data(), m.size());        }         return true;    }     const char* Name() const override { return "ProcessMerge"; }};

2、final:基类用final修饰其虚函数,以外其子类不可以多态继承该虚函数

class father {    public:        int a_;        int GetA() {return a_;}        virtual void SetA(int a) {            a_ = a;            LOG(INFO) << "father modify a to " << a_;        }        //add keyword final to avoid non-anticipated inherit in compling but not errored in running        //virtual void SetA(int a) final {a_ = a;}    public:        father(int a):a_(a) {}    };     class Son: public father {        int b_;    public:        Son(int a, int b):father(a), b_(b) {}        //add keyword override to avoid the error in compling but not errored in running.(eg. 'int SetA(double a){...} override' woule be errored by compiler)        virtual void SetA(int a) override {            a_ = a;            LOG(INFO) << "son modify a to " << a_;        }        //virtual void SetA(double a) override {a_ = a;}    };

如father基类的SetA实现为"virtual void SetA(int a) final {a_ = a;}",则子类Son再多态继承实现SetA方法就会报错了。

6964f9013eff439d77660b7035219a2e.png
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值