【问题标题】:C++ type traits to extract template parameter classC++ 类型特征提取模板参数类
【发布时间】:2012-06-15 19:03:35
【问题描述】:

在模板中,我想将模板参数向下钻取到真正的非模板类型。所以:

template <typename T>
struct MyTemplate
{
    // sadly there's no extract_Base
    typedef typename extract_base<T>::MyType WorkType;
};
struct X {};
template <typename T> struct Templ {};
//MyTemplate<Templ<X>>::WorkType is X;
//MyTemplate<X>::WorkType is X;

我看到的唯一解决方案是定义真正的基本类型,如 std::vector::value_type is X。但我很好奇是否有一种方法可以做到这一点,而无需在每个目标模板中定义辅助类型。

我看到了类似http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2009/n2965.html 的内容,但这是草稿吗?我不太明白。

是的,我知道有多重继承,但即使是简单的情况,这也很好。

更新:Nawaz 解决方案非常适合我,并且很容易扩展到特定情况,例如

template<template<typename, typename> class X, typename T1, typename T2>
struct extract_base <X<T1, T2>>   //specialization
{
    typedef T1 base;
};

我什至可以将 is_base_of 或其他过滤器应用于 T1/T2 等等。所以它确实适用于 X - 至少对于 g++ 4.6.7。

【问题讨论】:

  • 这与继承或基类无关。
  • std::is_base_of,但这可能不完全适合您的目的。

标签: c++ templates metaprogramming typetraits


【解决方案1】:

首先,我们称它为value_type 而不是base,因为value_type 似乎更适合描述您要提取的类型。

你可以用这个:

template<typename T>
struct extract_value_type //lets call it extract_value_type
{
    typedef T value_type;
};

template<template<typename> class X, typename T>
struct extract_value_type<X<T>>   //specialization
{
    typedef T value_type;
};

只要extract_value_type 的模板参数是TX&lt;T&gt; 的形式,它就应该工作。但是,它不适用于X&lt;T,U&gt;。但是使用可变参数模板在 C++11 中很容易实现。

将其用作:

template <typename T>
struct MyTemplate
{
    typedef typename extract_value_type<T>::value_type value_type;
};

在线演示:http://ideone.com/mbyvj


现在在 C++11 中,您可以使用可变参数模板使 extract_value_type 与接受多个模板参数的类模板一起工作,例如 std::vectorstd::setstd::list 等。

template<template<typename, typename ...> class X, typename T, typename ...Args>
struct extract_value_type<X<T, Args...>>   //specialization
{
    typedef T value_type;
};

演示:http://ideone.com/SDEgq

【讨论】:

  • 用“template class X”编译并且确实有效!谢谢。
  • @queen3:现在看看可变参数解决方案。
  • 是的,虽然 X 对我有用,请参阅更新。尽管如此,这正是我所需要的。
  • @queen3:我重命名了结构名称和嵌套类型。现在看看。 value_typebase 更适合。
  • 嗯,在我的例子中它是模板 X: public T 所以它真的是基础。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-09-08
  • 1970-01-01
  • 1970-01-01
  • 2012-04-23
  • 2023-04-04
  • 2020-04-29
相关资源
最近更新 更多