【问题标题】:Any way to initialize this variable based on class template type?有什么方法可以根据类模板类型初始化这个变量吗?
【发布时间】:2021-01-02 13:13:34
【问题描述】:

我有一个带有模板的类stats,以便它可以灵活使用。不过,我是模板的新手,我认为它们的目的是让它在用户周围变得灵活。所以当我撞到一堵小墙时,我觉得我做错了什么。

#include <iostream>
#include <cstdio>
#include <iomanip>

template <typename T>
class stats
{
    private:
        int n;
        T sum;
    public:
        stats()
        {
            this->n = 0;
            this->sum = T();
        }
        void push(T a);
        void print();
};

int main()
{
    std::string tmp; // change type based on class type T
    stats<std::string> s;
    while (std::cin >> tmp) // while input is active...
    {
        s.push(tmp);
    }

    // Output & Formatting
    s.print();
    return 0;
}
template <typename T>
void stats<T>::push(T a)
{
    this->sum += a;
    ++this->n;
}
template <typename T>
void stats<T>::print()
{
    std::cout   << std::left << std::setw(4) << "N"   << "= " << n   << '\n'
                << std::left << std::setw(4) << "sum" << "= " << sum << '\n';
}

来自int main(),理想情况下,我希望每次尝试不同类型时都不必自己更改 tmp。这在 C++ 中可行吗?

【问题讨论】:

    标签: c++ class templates


    【解决方案1】:

    惯用的方法是公开类型别名:

    template <typename T>
    class stats
    {
    public:
        using value_type = T;
    
        // ...
    };
    

    然后在你的主要:

    int main()
    {
        stats<std::string> s;
        decltype(s)::value_type tmp;
        while (std::cin >> tmp)
        {
            s.push(tmp);
        }
    
        // ...
    }
    

    这样,tmp 将始终采用 T 的类型。

    为了简化你的主要功能,你也可以在那里使用别名:

    int main()
    {
        using stats_t = stats<std::string>;
        stats_t s;
        stats_t::value_type tmp;
        while (std::cin >> tmp)
        {
            s.push(tmp);
        }
    
        // ...
    }
    

    【讨论】:

      【解决方案2】:

      对于不提供value_type 成员类型的类的另一个选项是使用函数来提取模板类型,例如

      template <template <typename...> typename Type, typename... Ts> 
      auto get_first_template_parameter(Type<Ts...>) -> std::tuple_element_t<0, std::tuple<Ts...>>;
      
      template <typename T>
      using value_type = decltype(get_first_template_parameter(std::declval<T>()));
      

      get_first_template_parameter 是一个元函数,仅用于获取模板类型的第一个类型,因此它不需要正文。然后 using 语句使用它,因此您可以拥有如下类型:

      stats<std::string> s;
      value_type<decltype(s)> tmp; // changes type based on class type T
      while (std::cin >> tmp) // while input is active...
      {
          s.push(tmp);
      }
      

      【讨论】:

        猜你喜欢
        • 2016-05-11
        • 2020-11-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-06-12
        • 1970-01-01
        相关资源
        最近更新 更多