【问题标题】:is it possible to make template auto cast c-string to c++ string object?是否可以使模板自动将 c-string 转换为 c++ 字符串对象?
【发布时间】:2014-05-05 16:39:20
【问题描述】:

这里的第一个函数在输入时编译并自动将 c char 数组转换为 c++ 字符串,但是当我尝试使用模板将该函数概括为其他类型时,它变得“愚蠢”并说它不理解该类型。

模板是否可以让函数自动从 char* 转换为 std::string 以及从 w_chart* 自动转换为 std::wstring,就像在普通函数定义中发生的那样?

#include <iostream>
#include <vector>
#include <string>

using namespace std;
vector<string> my_vector = { "apples", "bananas", "peaches"};

bool vector_has_item1(vector<string> v, string value_to_check) {
  for (string s : v) {
    if (s == value_to_check) return true;
  }
  return false;
}

template <typename T>
bool vector_has_item2(vector<T> v, T value_to_check) {
  for (T s : v) {
    if (s == value_to_check) return true;
  }
  return false;
}

int main() {
  cout << vector_has_item1(my_vector, "bananas") << endl;
  cout << vector_has_item2(my_vector, "bananas") << endl;
}

错误是:

test.cpp:25:48: error: no matching function for call to
 'vector_has_item2(std::vector<std::basic_string<char> >&, const char [8])'

【问题讨论】:

    标签: c++ string templates c-strings


    【解决方案1】:

    不要让T的类型由第二个参数确定,而是利用vector中的内置typedefs强制T由第一个参数确定,并强制第二个参数的类型由第一个参数确定第一个:

    #include <iostream>
    #include <vector>
    #include <string>
    #include <algorithm>
    
    using namespace std;
    vector<string> my_vector = { "apples", "bananas", "peaches"};
    
    bool vector_has_item1(vector<string> v, string value_to_check)
    {
        return std::find(v.begin(), v.end(), value_to_check) != v.end();
    }
    
    template <typename T>
    bool vector_has_item2(vector<T> v, typename vector<T>::value_type value_to_check)
    {
        return std::find(v.begin(), v.end(), value_to_check) != v.end();
    }
    
    int main()
    {
      cout << vector_has_item1(my_vector, "bananas") << endl;
      cout << vector_has_item2(my_vector, "bananas") << endl;
    }
    

    【讨论】:

      【解决方案2】:

      对于类型依赖于参与模板参数推导的模板参数的参数,不允许使用隐式转换 (*)(参见 C++11 §14.8.2.1/4)。

      因此,在推导出模板参数时

      template <typename T>
      bool vector_has_item2(vector<T> v, T value_to_check)
      

      T 不能推导出为std::string,因为第二个参数不是std::string 类型,也不是std::string 的较少cv 限定版本,也不是std::string 的派生类。另一方面,非模板函数

      bool vector_has_item3(vector<string> v, string value_to_check)
      

      确实可以使用参数my_vector"bananas"调用没有任何问题,因为不涉及模板参数推导,并且对"bananas"执行隐式转换以初始化参数value_to_check

      (*)大多数隐式转换,无论如何——当然还有所有用户定义的转换。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2023-03-14
        • 1970-01-01
        • 2012-12-03
        • 1970-01-01
        • 1970-01-01
        • 2022-01-01
        • 2011-09-30
        相关资源
        最近更新 更多