将字符数组转换为单个整数?

31

有人知道如何将字符数组转换为单个整数吗?

char hello[5];
hello = "12345";

int myNumber = convert_char_to_int(hello);
Printf("My number is: %d", myNumber);

1
这段代码能直接编译吗?不应该可以。 - Chris Lutz
它本来就不应该这样。convert_char_to_int(hello) 不是一个真正的函数。我想知道用什么函数/方法来替换我的理论上的 "convert_char_to_int(hello)"? - IsThisTheEnd
2
“hello”是一个不可修改的lvalue,所以hello = "12345";甚至无法编译。 - Prasoon Saurav
好的,那这个:http://codepad.org/oSgK5nK4 我该如何转换它? - IsThisTheEnd
1
你是否完全被C风格的构造如char数组和printf卡住了?如果不是,可以看看std::string来处理字符,使用C++ iostreams来打印输出(std::cout),并使用boost::lexical_cast进行转换(正如已经指出的那样)。 - juanchopanza
你给一个大小为5的数组分配了6个字符。记得要加上空字符终止符。最好使用字符串。如果不行,至少在声明时进行初始化以避免出现这样的问题。char hello[] = "12345"; - FalcoGer
9个回答

46

将字符串转换为整数有多种方法。

解决方案1:使用Legacy C功能

int main()
{
    //char hello[5];     
    //hello = "12345";   --->This wont compile

    char hello[] = "12345";

    Printf("My number is: %d", atoi(hello)); 

    return 0;
}

解决方案2:使用lexical_cast(最合适和最简单的方法)

int x = boost::lexical_cast<int>("12345"); 

解决方案3:使用C++ Streams

std::string hello("123"); 
std::stringstream str(hello); 
int x;  
str >> x;  
if (!str) 
{      
   // The conversion failed.      
} 

3
使用 boost::lexical_castatoi 不安全! - Nawaz
1
顺便说一下,你应该将 boost::lexical_cast 放在 try-catch 块中。当转换无效时,它会抛出 boost::bad_lexical_cast 异常。 - Nawaz
6
应该使用strtol而不是atoi,在这种情况下更加适合-没有必要仅为这个简单的操作而使用boost。 - Nim
1
为什么atoi不安全? - qed
1
C++11中的stoi和stol函数怎么样?例如std::stoi("1234") - qed
显示剩余5条评论

11
如果你在使用C++11,你应该使用stoi,因为它可以区分错误和解析0。
try {
    int number = std::stoi("1234abc");
} catch (std::exception const &e) {
    // This could not be parsed into a number so an exception is thrown.
    // atoi() would return 0, which is less helpful if it could be a valid value.
}

需要注意的是,在传递给 stoi() 函数之前,“1234abc”从一个 char[] 隐式转换为 std:string。保留implicitly converted链接。

3

我使用:

int convertToInt(char a[1000]){
    int i = 0;
    int num = 0;
    while (a[i] != 0)
    {
        num =  (a[i] - '0')  + (num * 10);
        i++;
    }
    return num;;
}

@Fateh,你是不是把字符“0”(数字零的字符,ASCII码为48)和实际的0字节值混淆了,后者表示字符串的结束? - user1079505

1

使用sscanf

/* sscanf example */
#include <stdio.h>

int main ()
{
  char sentence []="Rudolph is 12 years old";
  char str [20];
  int i;

  sscanf (sentence,"%s %*s %d",str,&i);
  printf ("%s -> %d\n",str,i);

  return 0;
}

不管怎样,千万不要使用"%s",因为那会导致缓冲区溢出。总的来说,stdtol更简单、更安全。 - James Kanze
1
strtol不是更好吗?为什么strtolatoi更好? - qed
对于atoi函数,“如果结果的值无法表示,则行为未定义”。而对于strtol函数,所有输入的行为都是定义好的。 - William Pursell

1
例如,"mcc"是一个字符数组,"mcc_int"是您想要获取的整数。
char mcc[] = "1234";
int mcc_int;
sscanf(mcc, "%d", &mcc_int);

1

我只是将这个留在这里,供那些对没有依赖关系的实现感兴趣的人参考。

inline int
stringLength (char *String)
    {
    int Count = 0;
    while (*String ++) ++ Count;
    return Count;
    }

inline int
stringToInt (char *String)
    {
    int Integer = 0;
    int Length = stringLength(String);
    for (int Caret = Length - 1, Digit = 1; Caret >= 0; -- Caret, Digit *= 10)
        {
        if (String[Caret] == '-') return Integer * -1;
        Integer += (String[Caret] - '0') * Digit;
        }

    return Integer;
    }

适用于负值,但无法处理混合了非数字字符的情况(不过添加应该很容易)。仅限整数。

0

使用 cstring 和 cmath 库:

int charsToInt (char* chars) {

    int res{ 0 };

    int len = strlen(chars);

    bool sig = *chars == '-';
    if (sig) {
        chars++;
        len--;
    }

    for (int i{ 0 }; i < len; i++) {
        int dig = *(chars + i) - '0';
        res += dig * (pow(10, len - i - 1));
    }

    res *= sig ? -1 : 1;

    return res;
}

-1

将Ascii字符串转换为整数是通过atoi()函数完成的。


3
那是你绝对应该避免的一个。你如何检查错误? - James Kanze

-2
长话短说,你必须使用atoi()
ed:
如果你有兴趣以正确的方式完成这个任务:
char szNos[] = "12345";
char *pNext;
long output;
output = strtol (szNos, &pNext, 10); // input, ptr to next char in szNos (null here), base 

2
不,你不应该在任何新代码中这样做 - 而是使用 strtol - Nim
@Nim 我知道这一点,但对于像 OP 这样的新手来说,让他/她使用它可能是可以的,只是为了理解这个概念。我想这也是其他人建议使用同样的 API 的原因。 - Reno
@harper,标准C++中没有itoa函数。传统接口已经过时,可能导致缓冲区溢出。 - James Kanze
2
@Reno 在任何情况下,都不应该鼓励初学者养成不良习惯。 - James Kanze

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接