使用stringstream将字符串转换为数字

时间:2017-11-10 14:08:39

标签: c++ templates stringstream

我想实现这样的功能:

template <class C>
C string_to_number(const string &s){
    stringstream ss(s);
    C num;
    ss >> num;
    return num;
}

但它会导致错误。我可以在没有class C但只有double string_to_number(const string &s)int string_to_number(const string &s)这样的数据类型的情况下执行此操作,但我不能同时使用这两种数据类型。

我该怎么做才能使用这样的函数:

int main()
{
    string s = "12.75";
    double d = string_to_number(s); // be 12.75
    int i = string_to_number(s); // be 12
}

有谁知道有办法吗?

3 个答案:

答案 0 :(得分:1)

模板参数C仅用作函数返回值的类型,而不是函数参数,它不能是deduced

  

如果可能,编译器将从函数参数推断出缺少的模板参数。

您必须明确指定模板参数,例如

double d = string_to_number<double>(s); // be 12.75
int i = string_to_number<int>(s); // be 12

答案 1 :(得分:1)

可以通过user-defined conversion operators模拟退货类型扣除:

#include <sstream>
#include <string>

class string_to_number final
{
public:
    string_to_number(const std::string& string)
        : string_{string}
    {
    }

    string_to_number(const string_to_number&) = delete;

    template <class Type>
    operator Type() const &&
    {
        std::stringstream string_stream{string_};
        Type value;

        string_stream >> value;

        return value;
    }

private:
    const std::string& string_;
};

// ...

std::string s = "12.75";
double d = string_to_number(s); // be 12.75
int i = string_to_number(s); // be 12

Live demo

答案 2 :(得分:0)

采取这一行

double d = string_to_number(s); // be 12.75

编译器必须实例化函数模板string_to_number。对于模板参数的推导,既没有显式的模板参数列表,也没有推导出的函数参数。除此之外,没有其他机制来推断模板参数。特别是返回值将考虑用于模板参数推断,正如您的代码想要建议的那样。

由于函数参数不对模板参数有任何依赖性,您必须指定显式模板参数:

double d = string_to_number<double>(s); // be 12.75

感谢auto,您可以删除冗余:

auto d = string_to_number<double>(s); // be 12.75