Как определить, является ли строка числом с C ++? - PullRequest
106 голосов
/ 11 января 2011

У меня было немало проблем при попытке написать функцию, которая проверяет, является ли строка числом.Для игры, которую я пишу, мне просто нужно проверить, является ли строка из файла, который я читаю, числом или нет (я буду знать, является ли это параметром таким образом).Я написал нижеприведенную функцию, которая, по моему мнению, работала гладко (или я случайно отредактировал ее, чтобы остановить, или я шизофреник, или Windows шизофреник):

bool isParam (string line)
{
    if (isdigit(atoi(line.c_str())))
        return true;

    return false;
}

Ответы [ 30 ]

1 голос
/ 02 ноября 2017

Мы можем использовать класс stringstream .

    bool isNumeric(string str)
    {
       stringstream stream;                   
       double number;

       stream<<str;
       stream>>number;

       return stream.eof();
    }
1 голос
/ 15 марта 2017

Как мне показалось в ответе на мой связанный вопрос, я чувствую, что вы должны использовать boost :: convert :: try_lexical_convert

1 голос
/ 05 февраля 2017

Мое решение, использующее регулярное выражение C ++ 11 (#include <regex>), его можно использовать для более точной проверки, например unsigned int, double и т. Д.в http://ideone.com/lyDtfi, это может быть легко изменено для соответствия требованиям.

0 голосов
/ 28 мая 2019
Стиль

C / C ++ для целых чисел без знака с использованием диапазонов for C ++ 11:

int isdigits(const std::string & s)
{
    for (char c : s) if (!isdigit(c)) return (0);
    return (1);
}
0 голосов
/ 16 апреля 2019

Попробуйте это:

bool checkDigit(string str)
{  
   int n=str.length();

   for(int i=0;    i   < n ;   i++)
   {
     if(str[i]<'0' || str[i]>'9')
       return false;
   }

   return true;
}
0 голосов
/ 01 декабря 2018

Не могли бы вы просто использовать код возврата sscanf, чтобы определить, является ли это int?

bool is_number(const std::string& s)
{
    int value;
    int result = sscanf(valueStr.c_str(), "%d", &value);
    return (result != EOF && readResult != 0);
}
0 голосов
/ 03 апреля 2018

Эта функция заботится обо всех возможных случаях:

bool AppUtilities::checkStringIsNumber(std::string s){
    //Eliminate obvious irritants that could spoil the party
    //Handle special cases here, e.g. return true for "+", "-", "" if they are acceptable as numbers to you
    if (s == "" || s == "." || s == "+" || s == "-" || s == "+." || s == "-.") return false;

    //Remove leading / trailing spaces **IF** they are acceptable to you
    while (s.size() > 0 && s[0] == ' ') s = s.substr(1, s.size() - 1);
    while (s.size() > 0 && s[s.size() - 1] == ' ') s = s.substr(0, s.size() - 1);


    //Remove any leading + or - sign
    if (s[0] == '+' || s[0] == '-')
        s = s.substr(1, s.size() - 1);

    //Remove decimal points
    long prevLength = s.size();

    size_t start_pos = 0;
    while((start_pos = s.find(".", start_pos)) != std::string::npos) 
        s.replace(start_pos, 1, "");

    //If the string had more than 2 decimal points, return false.
    if (prevLength > s.size() + 1) return false;

    //Check that you are left with numbers only!!
    //Courtesy selected answer by Charles Salvia above
    std::string::const_iterator it = s.begin();
    while (it != s.end() && std::isdigit(*it)) ++it;
    return !s.empty() && it == s.end();

    //Tada....
}
0 голосов
/ 15 августа 2014

Несколько месяцев назад я реализовал способ определения, является ли любая строка целочисленной, шестнадцатеричной или двойной.

enum{
        STRING_IS_INVALID_NUMBER=0,
        STRING_IS_HEXA,
        STRING_IS_INT,
        STRING_IS_DOUBLE
};

bool isDigit(char c){
    return (('0' <= c) && (c<='9'));
}

bool isHexaDigit(char c){
    return ((('0' <= c) && (c<='9')) || ((tolower(c)<='a')&&(tolower(c)<='f')));
}


char *ADVANCE_DIGITS(char *aux_p){

    while(CString::isDigit(*aux_p)) aux_p++;
    return aux_p;
}

char *ADVANCE_HEXADIGITS(char *aux_p){

    while(CString::isHexaDigit(*aux_p)) aux_p++;
    return aux_p;
}


int isNumber(const string & test_str_number){
    bool isHexa=false;
    char *str = (char *)test_str_number.c_str();

    switch(*str){
    case '-': str++; // is negative number ...
               break;
    case '0': 
              if(tolower(*str+1)=='x')  {
                  isHexa = true;
                  str+=2;
              }
              break;
    default:
            break;
    };

    char *start_str = str; // saves start position...
    if(isHexa) { // candidate to hexa ...
        str = ADVANCE_HEXADIGITS(str);
        if(str == start_str)
            return STRING_IS_INVALID_NUMBER;

        if(*str == ' ' || *str == 0) 
            return STRING_IS_HEXA;

    }else{ // test if integer or float
        str = ADVANCE_DIGITS(str);
        if(*str=='.') { // is candidate to double
            str++;
            str = ADVANCE_DIGITS(str);
            if(*str == ' ' || *str == 0)
                return STRING_IS_DOUBLE;

            return STRING_IS_INVALID_NUMBER;
        }

        if(*str == ' ' || *str == 0)
            return STRING_IS_INT;

    }

    return STRING_IS_INVALID_NUMBER;


}

Тогда в вашей программе вы можете легко преобразовать число в функцию в ее тип, если вы выполнитезатем,

string val; // the string to check if number...

switch(isNumber(val)){
   case STRING_IS_HEXA: 
   // use strtol(val.c_str(), NULL, 16); to convert it into conventional hexadecimal
   break;
   case STRING_IS_INT: 
   // use (int)strtol(val.c_str(), NULL, 10); to convert it into conventional integer
   break;
   case STRING_IS_DOUBLE:
   // use atof(val.c_str()); to convert it into conventional float/double
   break;
}

Вы можете понять, что функция вернет 0, если номер не был обнаружен.Значение 0 может рассматриваться как ложное (как логическое значение).

0 голосов
/ 01 марта 2017

Еще один ответ, который использует stold (хотя вы также можете использовать stof / stod, если вам не требуется точность).

bool isNumeric(const std::string& string)
{
    std::size_t pos;
    long double value = 0.0;

    try
    {
        value = std::stold(string, &pos);
    }
    catch(std::invalid_argument&)
    {
        return false;
    }
    catch(std::out_of_range&)
    {
        return false;
    }

    return pos == string.size() && !std::isnan(value);
}
0 голосов
/ 26 ноября 2014

Я предлагаю простое соглашение:

Если преобразование в ASCII> 0 или начинается с 0, то это число. Это не идеально, но быстро.

Примерно так:

string token0;

if (atoi(token0.c_str())>0 || isdigit(token0.c_str()[0]) ) { //this is a value
    // do what you need to do...
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...