8

Hello I know it was asked many times but I hadn't found answer to my specific question.

I want to convert only string that contains only decimal numbers:

For example 256 is OK but 256a is not.

Could it be done without checking the string?

Thanks

2
  • 2
    Your subject line says "convert integer to string", but your question kind of seems to imply a string-to-int conversion... what are you trying to do?! Commented Oct 4, 2010 at 20:50
  • 1
    This post is vague and needs more punctuation. Could you explain what you mean with an example? Commented Oct 4, 2010 at 20:51

4 Answers 4

14

The simplest way that makes error checking optional that I can think of is this:

char *endptr;
int x = strtol(str, &endptr, 0);
int error = (*endptr != '\0');
Sign up to request clarification or add additional context in comments.

1 Comment

I'm not a fan of atoi since it provides no way of telling the difference between a completely invalid string and a string which is valid and converts to 0
7

In C++ way, use stringstream:

#include <iostream>
#include <string>
#include <sstream>
using namespace std;

int main()
{
    stringstream sstr;
    int a = -1;

    sstr << 256 << 'a';
    sstr >> a;

    if (sstr.failbit)
    {
        cout << "Either no character was extracted, or the character can't represent a proper value." << endl;
    }
    if (sstr.badbit)
    {
        cout << "Error on stream.\n";
    }

    cout << "Extracted number " << a << endl;

    return 0;
}

2 Comments

but what if the string is not an integer? what will be the value of a ?
@Jean-FrançoisFabre: You can check stream condition by verifying the state returned by sstr.rdstate(), or by checking individual state values. I've updated my answer with the latter choice.
6

An other way using c++ style : We check the number of digits to know if the string was valid or not :

#include <iostream>
#include <sstream>
#include <string>
#include <cmath>

int main(int argc,char* argv[]) {

    std::string a("256");

    std::istringstream buffer(a);
    int number;
    buffer >> number; // OK conversion is done !
    // Let's now check if the string was valid !
    // Quick way to compute number of digits
    size_t num_of_digits = (size_t)floor( log10( abs( number ) ) ) + 1;
    if (num_of_digits!=a.length()) {
        std::cout << "Not a valid string !" << std::endl;
    }
    else {
        std::cout << "Valid conversion to " << number  << std::endl;
    }

}

1 Comment

Fails for "0", "0001", "-5".
0

In C++17 and above the best way is to use std::from_chars() from the header charconv. Unlike other solutions, this one handles overflows automatically in a neat way. It is also locale-independent, non-allocating, and non-throwing and hence the performance is expected to be better than solutions based on string streams. You may find more information in cppreference.

The following example is taken from cppreference.

#include <cassert>
#include <charconv>
#include <iomanip>
#include <iostream>
#include <string_view>
#include <system_error>
 
int main()
{
    for (std::string_view const str : {"1234", "15 foo", "bar", " 42", "5000000000"})
    {
        std::cout << "String: " << std::quoted(str) << ". ";
        int result{};
        auto [ptr, ec] = std::from_chars(str.data(), str.data() + str.size(), result);
 
        if (ec == std::errc())
            std::cout << "Result: " << result << ", ptr -> " << std::quoted(ptr) << '\n';
        else if (ec == std::errc::invalid_argument)
            std::cout << "This is not a number.\n";
        else if (ec == std::errc::result_out_of_range)
            std::cout << "This number is larger than an int.\n";
    }
}

Demo: https://godbolt.org/z/ohxWEbnTb

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.