使用stoi()与substr()将字符串转int数组抛出stoi异常如何解决
错误原因
- 核心触发点是
substr参数传错:C++标准库中string::substr的第一个参数是子串起始下标,第二个参数是子串的截取长度。你写的input.substr(i,i)在第一次循环i=0时,截取长度为0,得到的是空字符串,stoi无法对空串做整数转换,直接抛出std::invalid_argument异常,就是你看到的报错信息。 - 就算跳过i=0的情况,后续
substr(i,i)的逻辑也完全不符合逐位取数字的需求:i=1时会从下标1开始截1个字符,i=2时从下标2开始截2个字符,取出来的不是单个数字,转换结果完全不符合预期。 - 输入读取逻辑有缺陷:
cin >> input遇到空格、换行就会终止读取,如果输入的数字之间带分隔空格,无法读到完整输入;同时代码没有校验输入长度、没有判断字符是否为有效数字,输入长度不足5位、包含非数字字符时都会触发异常。
修改方案
如果你的需求是把字符串里的单个数字字符逐位转成0-9的整数,存入长度为5的int数组,不需要用stoi,直接利用数字字符的ASCII编码连续的特性做转换即可,同时补全输入校验逻辑,修正后的代码如下:
#include <iostream> #include <string> #include <cctype> using namespace std; int main() { int number[5]; string input; cout << "type some numbers" << endl; getline(cin, input); // 读取整行输入,避免空格截断 int idx = 0; for (char c : input) { // 只处理数字字符,数组存满5个就停止 if (isdigit(c) && idx < 5) { number[idx] = c - '0'; // 数字字符减'0'直接得到对应整数值 cout << number[idx] << " "; idx++; } } if (idx < 5) { cout << endl << "提示:输入有效数字不足5个,仅成功读取" << idx << "个数字" << endl; } return 0; }
如果你坚持要用stoi实现,需要把substr的第二个参数固定为1(每次只截1个字符),同时加上边界和内容校验,避免传入无效字符串:
// 核心循环替换为如下写法 for(int i = 0 ; i<= 4; i++){ if (i >= input.size() || !isdigit(input[i])) { cout << endl << "位置" << i << "不存在有效数字" << endl; break; } number[i] = stoi(input.substr(i,1), nullptr, 10); cout << number[i] << " "; }
注意:如果你的需求是读取5个多位整数(比如输入
12 34 56 78 90这种,每个数组元素存一个多位数),则需要先按分隔符拆分字符串后再逐个转换,不能直接逐位截取。
内容的提问来源于stack exchange,提问作者Daniel
相关产品推荐
相关产品推荐

