是否可以在概念中指定模板化 class?

is it possible to specify templated class in concepts?

假设我有一个将字符串转换为数字类型的函数,如下所示

template<class T>
T to_t(const std::string& str) {
    return boost::lexical_cast<T>(str);
}

并且我想让函数能够将数字 str 转换为 std::chrono::duration,这样我就可以编写类似 to_t<std::chrono::seconds>("1234") to_t<std::chrono::nanoseconds>("1234")

的代码

我想使用概念来实现它,但无法弄清楚如何为 std::chrono::duration 的类型编写约束,因为这是一个带有模板参数的 class。

如果概念在这里不适用,那么为 std::chrono::duration 实现此功能的推荐方法是什么?谢谢

是的,您可以创建持续时间概念。

std::duration

成员的任何内容
template <std::regular T>
concept duration = requires (T a, T b, typename T::rep r) {
    typename T::rep;
    typename T::period;
    { a + b } -> std::same_as<T>;
    { a - b } -> std::same_as<T>;
    { a * r } -> std::same_as<T>;
    { r * a } -> std::same_as<T>;
    { a / r } -> std::same_as<T>;
    { a / b } -> std::same_as<T>;
    { a % r } -> std::same_as<T>;
    { a % b } -> std::same_as<T>;
}

或者具体来说,如果它是一个实例化

template <typename T>
struct is_duration : std::false_type {};

template <typename Rep, typename Period>
struct is_duration<std::duration<Rep, Period>> : std::true_type {};

template <typename T>
concept duration = is_duration<T>::value

你的概念可以定义为:

template <class Dur>
concept stl_duration = std::same_as<
  Dur, std::chrono::duration<typename Dur::rep, typename Dur::period>
>;

或者更一般地,使用 Specializes:

template <typename T, template <typename...> class Z>
inline constexpr bool is_specialization_of = false;

template <template <typename...> class Z, class... Args>
inline constexpr bool is_specialization_of<Z<Args...>, Z> = true;

template <typename T, template <typename...> class Z>
concept Specializes = is_specialization_of<T, Z>;

template <class Dur>
concept stl_duration = Specializes<Dur, std::chrono::duration>;

那么你的to_t可以定义为:

template<stl_duration T>
T to_t(const std::string& str) {
  return boost::lexical_cast<T>(str);
}

Demo.