仅在C ++中的const限定符上实现模板

时间:2019-11-19 23:02:15

标签: c++ templates const

我想得到两个仅在参数的恒定性上不同的类。

我目前正在做的是:
(这是一个虚拟的最小示例。)

template <typename T>
struct Wrapper {
    Wrapper(T & t):
        t(t) {
    }

    T & t;
};

class Foo;

using Foo_wrapper = Wrapper<Foo>;
using Const_Foo_wrapper = Wrapper<const Foo>;

我希望我的模板仅在Foo上声明,并且仅在const限定符上有所不同。
诸如:
(这是无效的语法,试图说明问题。)

class Foo;

template <qualifier Q>
struct Foo_base_wrapper {
    Wrapper(Q Foo & t):
        t(t) {
    }

    Q Foo & t;
};

using Foo_wrapper = Foo_base_wrapper<none>;
using Const_Foo_wrapper = Foo_base_wrapper<const>;

有没有办法做到这一点?

(一个接近的解决方案可能是概念,但这将更加通用和复杂,并且我没有C ++ 20。)

1 个答案:

答案 0 :(得分:2)

您不能单独使用const关键字,而可以使用模板(部分)专业化来控制具有这种类型的类型的常数。

enum Qualifier { Mutable, Const };

template<typename T, Qualifier Q>
struct Qualified
{
    using type = T;
};

template<typename T>
struct Qualified<T, Const>
{
    using type = const T;
};

template <Qualifier Q = Mutable>
struct Foo_base_wrapper
{
    using QualifiedFoo = typename Qualified<Foo, Q>::type;

    Foo_base_wrapper(QualifiedFoo & t) : t(t)
    { }

    QualifiedFoo & t;
};

using Foo_wrapper = Foo_base_wrapper<>;  // or explicitly Foo_base_wrapper<Mutable>
using Const_Foo_wrapper = Foo_base_wrapper<Const>;

如果您不必定义其他包装器,则当然可以在Qualified模板及其专业化中直接使用Foo。

您可能还对处理引用常量的功能std::ref / std::cref感兴趣。