繁体   English   中英

仅在模板类的特定特化上声明成员函数

[英]Declare member function only on specific specialization of templated class

我有一个模板类来帮助物理量的编译时计算。 它使用额外的模板参数( std::ratio )来确保只能将Length之类的内容添加到Length中,或者AreaLength乘以Length

#include <ratio>

template <
  typename Length      = std::ratio<0>, // Meter
  typename Mass        = std::ratio<0>, // Kilogram
  typename Time        = std::ratio<0>, // Second
  typename Current     = std::ratio<0>, // Ampere
  typename Temperature = std::ratio<0>, // Kelvin
  typename Amount      = std::ratio<0>, // Mole
  typename Luminous    = std::ratio<0>  // Candela
>
class Quantity {
private:
  double value;
public:
  constexpr Quantity(double val) : value(val) {}

  Quantity &operator+=(Quantity const &that) {
    value += that.value;
    return *this;
  }

  // ...
};

但有时我想转换回一个简单的double ,以便与其他东西交互。

我可以为返回内部double精度的模板类添加一个成员函数 - 或者在需要double精度时启用隐式(或显式)转换为double精度。

  constexpr double getValue() { return value; }
  constexpr operator double() { return value; }

但是,我真的只希望在数量的“维度”全部为 0(所有模板参数为 0)时发生这种隐式转换。

我可以只声明相同的成员函数,只定义我想要的特化。 但这仍然声明对于我不想允许转换的类型存在转换(您应该首先除以所需的单位)。 这让我的编辑告诉我没关系,但它不会在编译时链接。

有没有办法只在某些特化上声明成员函数?

值得注意的是,我现在坚持使用 C++14,否则我认为if constexpr可以工作......

不, if constexpr不能用于提供类方法的条件定义。 if constexpr属于某个方法或函数,因此需要先声明它,然后才能使用if constexpr完成任何操作,而您的目标甚至是一开始就不要声明它。

没有办法只为某些特化或模板实例直接实例化类方法,但是有一种非常接近的通用方法:模拟重载解析失败。

这是一个简化的示例:

#include <type_traits>
#include <iostream>

template<typename T>
struct life {
    template<typename=
         typename std::enable_if<std::is_same<T,int>::value>::type>
    constexpr int answer()
    {
        return 42;
    }
};

int main()
{
    life<int> of_brian;

    std::cout << of_brian.answer() << std::endl; // Shows 42

    life<double> of_black_night;

    std::cout << of_black_night.answer() << std::endl; // Error
    return 0;
}

模板类仅对其int实例有效地实现answer() gcc的错误消息,用于尝试从不需要的模板实例调用它是:

错误:没有匹配函数调用 'life<double>::answer()'

这是“这不存在,伙计”的非常接近的传真。

这在逻辑上等同于您尝试对模板执行的操作,唯一的区别是您需要检查一堆模板参数,而不仅仅是一个。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM