使用stringstream将字符串转换为int的效率?

时间:2015-10-30 17:09:29

标签: c++ stringstream data-conversion

以下代码的效率是否低于(或更高,或同等):

make substring from cursor
make stringstream from substring
extract integer using stream operator

? (问题编辑)或者是否比(或更多,或同等)更有效:

std::stoi

?为什么?

这项功能能否提高效率?

(该课程将这些纳入范围:)

std::string expression  // has some numbers and other stuff in it
int cursor              // points somewhere in the string

代码:

int Foo_Class::read_int()
{
    /** reads an integer out of the expression from the cursor */

    // make stack of digits
    std::stack<char> digits;

    while (isdigit(expression[cursor]))  // this is safe, returns false, for the end of the string (ISO/IEC 14882:2011 21.4.5)
    {
        digits.push(expression[cursor] - 48);  // convert from ascii
        ++cursor;
    }

    // add up the stack of digits
    int total = 0;
    int exponent = 0;  // 10 ^ exponent
    int this_digit;

    while (! digits.empty())
    {
        this_digit = digits.top();
        for (int i = exponent; i > 0; --i)
            this_digit *= 10;
        total += this_digit;

        ++exponent;
        digits.pop();
    }

    return total;
}

(我知道它不会处理溢出。)

(我知道有人可能会对魔术数字说些什么。)

(我尝试过pow(10,exponent)并得到不正确的结果。我因为浮点运算而猜测,但不确定为什么因为所有数字都是整数。)

2 个答案:

答案 0 :(得分:2)

我发现使用std::stringstream来转换数字真的很慢。

最好使用许多专用号码转换功能,例如std::stoi, std::stol, std::stoll。或std::strtol, std::strtoll

答案 1 :(得分:1)

我在此页面上找到了很多信息: http://www.kumobius.com/2013/08/c-string-to-int/

正如Galik所说,与其他所有东西相比,std :: stringstream非常慢。

std :: stoi比std :: stringstream

快得多

手动代码可以更快,但正如已经指出的那样,它不会进行所有错误检查,并且可能会出现问题。

此网站还对上面的代码进行了改进,将总数乘以10,而不是将数字加到总数之前(按顺序排列,而不是反向,使用堆栈)。这样可以减少乘以10。

int Foo_Class::read_int()
{
    /** reads an integer out of the expression from the cursor */

    int to_return = 0;

    while (isdigit(expression[cursor]))  // this is safe, returns false, for the end of the string (ISO/IEC 14882:2011 21.4.5)
    {
        to_return *= 10;
        to_return += (expression[cursor] - '0');  // convert from ascii
        ++cursor;
    }

    return to_return;
}