郴州网站,网站建设面试对策,电脑怎样做轰炸网站,建设银行河北招聘网站一、继承
在c编程中#xff0c;一定是脱离不开继承的。而继承中有很多小的细节需要关注#xff0c;比如如何显示的使用父类的构造函数#xff1f;如何通过构造函数来推导模板参数等等。这些小的细节#xff0c;其实都是在实际应用中对一些相关技术的不断完善。
二、继承的…一、继承
在c编程中一定是脱离不开继承的。而继承中有很多小的细节需要关注比如如何显示的使用父类的构造函数如何通过构造函数来推导模板参数等等。这些小的细节其实都是在实际应用中对一些相关技术的不断完善。
二、继承的CTAD
在前面的《跟我学c高级篇——c17类模板实参推导CTAD》中已经知道在c17后放宽了对一些构造函数中的模板参数的显示指定而转为由编译器自动推导出来而今天就要分析一下在继承中的模板如何自动推导模板参数。 先回顾一下在c17中的构造函数的推导
//pre
std::mutex mt;
std::lock_guard lg{mt};
//c17
std::lock_guard lg{mt};那么就可以顺理的推导到从继承可以自动推导相关的模板参数。其实很容易理解子类当然可以调用父类的构造函数不就直接转过去了么有点类似于委托构造。看一个例子
struct A { A();A(int );... };
struct B : A
{using A::A;
};在更早期的版本中可以使用一个完美转发来实现显示的对父类的构造。但这都有一些问题。比如上面的代码中如果构造函数传入的参数是一个Lambda表达式即下面这种情况
template typename T
struct A {A(T t ):func_(t){}T func_;
};
template typename T
struct B : A
{using AT::A;
};如果直接使用A a({}),根据CTAD的推导它是正确的构造过程。但如果使用B类也如此构造则CTAD没法在这其中使用结果当然是编译失败。当然可以用一个auto类型存储一下这个表达式然后再decltype搞一下也能达到同样的目的可似乎有点小麻烦了。而在C23中则补齐了这个短板直接可以使用了。即也可以B b{{}}进行初始化。 不过这不代表着它是完美的举一个没有显示的构造函数情况下的例子就明白了
struct A { char a,b,c; };
struct B : A
{using A::A;
};一般使用初始化列表来对其进行定义即A a{‘a’,‘a’,‘b’};但对B b{‘a’,‘a’,‘b’}仍然会报错必须是模板参数推导这都没参数了推导个啥。
三、CTAD的例程
下面看一个简单的例程
templatetypename T
struct A
{A(T) {}
};templatetypename T
struct B : public AT
{using AT::A;
};templatetypename T
struct C : public AT
{ };B b{0}; // OK
C c(1); // ERR
A(int) - Achar; // 显示声明推导
B bb{2}; // OK参数int被推导为char是不是简单明了标准对相关的CTAD的完善越来越多以后应用起来相对来说会简单不少。
四、总结
从目前看来标准越是向前推进相关的完善和填坑的动作也越多。那么相对来说使用起来的通用性越好。而这也代表着编程相关对来说简单不少毕竟少了不少的特异性的处理后只要一般的应用即可。不用总想着这个特例那个特例。 简单才是王道 c23系列到这篇基本就终止了。以后再写可能就是偶尔补充一下了。可能也就是c26的新功能新属性了变化才是永恒啊