【发布时间】:2021-11-12 06:30:02
【问题描述】:
如果我想要一个具有可选成员的类,我正在使用模板专业化:
template<class T>
struct X {
T t;
void print() { cout << "t is " << t << '\n'; }
};
template<>
struct X<void> {
void print() { cout << "without T\n"; }
};
这很好,因为没有运行时开销和很少的代码重复。 但是,如果我有 3 个而不是 1 个可选类成员,我必须编写 2^3=8 个类,即“小重复”很快变得不合理。
一个可能的解决方案可能是像这样使用std::conditional:
template<class T1, class T2, class T3>
struct X {
conditional_t<is_void_v<T1>, char, T1> t1;
conditional_t<is_void_v<T2>, char, T2> t2;
conditional_t<is_void_v<T3>, char, T3> t3;
void print() {
if constexpr (!is_void_v<T1>) cout << "t1 is " << t1 << '\n';
if constexpr (!is_void_v<T2>) cout << "t2 is " << t2 << '\n';
if constexpr (!is_void_v<T3>) cout << "t3 is " << t3 << '\n';
}
};
但是现在,我班级的对象会浪费内存。我正在寻找某种方法来避免大部分代码重复(在可选成员代码开销的数量上最多呈线性),同时避免花费不必要的运行时间和内存。
请注意,对于单个可选类成员(请参阅Optional class members without runtime overhead、Most efficient way to implement template-based optional class members in C++?)存在此问题(有答案),但据我所知,对于多个可选成员,该问题尚未得到解答。
【问题讨论】:
-
也许你不知道,如果用户想查看你的问题的历史,他们可以在这里看到:stackoverflow.com/posts/69222391/revisions。您无需添加“编辑:...”或保留旧内容
-
可变参数模板是否可接受,或者
t1、t2、t3是真正不同的含义(即<int, void, int>和<int, int, void>)。 -
@463035818_is_not_a_number 我选择写“编辑:...”而不是更改问题,因为现在阅读您的评论的人可能会错误地认为它引用了当前形式的问题。跨度>
-
他们没有,因为评论被删除了 ;) 考虑到这种情况经常发生(cmets 指的是较旧的修订版)并且 cmets 的寿命相当短,而重要的是问题中的内容
-
@Jarod42 我不确定我是否理解这个问题。是的,
<int, void, int>应该是与<int, int, void>不同的类,但是,如果我理解正确的话,这与可变参数模板没有冲突。
标签: c++ templates optional-parameters