继承T
和使用时,有没有办法在模板中初始化 const 成员using T::T
?这是一个例子
#include <iostream>
#include <ctime>
#include <string>
#include <memory>
class A {
protected:
int wake_up_time_;
public:
A(int wake_up_time): wake_up_time_(wake_up_time) { }
virtual void hello() const {
std::cout << "I wake up at " << wake_up_time_;
}
};
/* B classes inherit from A and have different members some of which vary in
* size and type */
class B1 : public A {
public:
std::string b;
B1(int a, std::string b): A(a), b(b) { }
};
class B2 : public A {
public:
int c;
double d;
B2(int a, int c, double d): A(a), c(c), d(d) { }
};
template<class T>
class bird : public T {
/* this function is more expensive in my case. */
bool is_early_bird() const { // needs to be const as hello is const
return this->wake_up_time_ < 6;
}
/* would like to have this instead */
// const bool is_early_bird_;
public:
/* which we assign in the constructor */
using T::T;
void hello() const override {
std::cout << (is_early_bird() ? "I am an early bird!" : "Getting up is hard...")
<< std::endl;
}
};
template<class T>
class cat : public T {
/* similar comments as in bird class */
bool is_hunting() const {
return this->wake_up_time_ < 5 || this->wake_up_time_ > 22;
}
public:
using T::T;
void hello() const override {
std::cout << (is_hunting() ? "Time to kill stuff" : "Time to sleep")
<< std::endl;
}
};
int main() {
std::unique_ptr<A> ptr;
{
ptr.reset(new bird<B1>(5, "..."));
std::cout << "B1 has value " << dynamic_cast<B1*>(ptr.get())->b << std::endl;
}
ptr->hello();
{
ptr.reset(new cat<B1>(12, "xyz"));
std::cout << "B1 has value " << dynamic_cast<B1*>(ptr.get())->b << std::endl;
}
ptr->hello();
{
ptr.reset(new cat<B2>(24, 3, 12.5));
B2* l_ptr = dynamic_cast<B2*>(ptr.get());
std::cout << "B2 has value " << l_ptr->c << " and " << l_ptr->d << std::endl;
}
ptr->hello();
{
ptr.reset(new B2(10, 7, 3.33));
B2* l_ptr = dynamic_cast<B2*>(ptr.get());
std::cout << "B2 has value " << l_ptr->c << " and " << l_ptr->d << std::endl;
}
ptr->hello();
return 0;
}
输出是
B1 has value ...
I am an early bird!
B1 has value xyz
Time to sleep
B2 has value 3 and 12.5
Time to kill stuff
B2 has value 7 and 3.33
I wake up at 10
我想要摆脱的是(在这种情况下是简单的)计算,cat::is_hunting
并bird::is_early_bird
改为使用 const 成员。我还有很多函数将引用或指向B1
或B2
类的指针作为参数,因此它似乎不是拥有public cat : public A
和public bird : public A
类并以 2x2 继承的 B 类结尾的选项。
WF在评论区给出了答案。答案是改变,例如,cat
类
template<class T>
class cat : public T {
const bool is_hunting_ = { this->wake_up_time_ < 5 || this->wake_up_time_ > 22 };
public:
using T::T;
void hello() const override {
std::cout << (is_hunting_ ? "Time to kill stuff" : "Time to sleep")
<< std::endl;
}
};
从
template<class T>
class cat : public T {
/* similar comments as in bird class */
bool is_hunting() const {
return this->wake_up_time_ < 5 || this->wake_up_time_ > 22;
}
public:
using T::T;
void hello() const override {
std::cout << (is_hunting() ? "Time to kill stuff" : "Time to sleep")
<< std::endl;
}
};
这是在这个网站上描述的
成员初始化
非静态数据成员可以通过以下两种方式之一进行初始化:
...
2) 通过默认成员初始化器,它只是包含在成员声明中的大括号或等号初始化器,如果成员在成员初始值设定项列表。
...用法
非静态数据成员或非静态成员函数的名称只能出现在以下三种情况:
1) 作为类成员访问表达式的一部分,其中类要么具有此成员,要么派生自具有此成员的类,包括this->
在任何允许使用的上下文中使用非静态成员名称时出现的隐式成员访问表达式...
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句