C++ 从字符串读取/解析多个整数

C++ 从字符串读取/解析多个整数,c++,c,string,robot,C++,C,String,Robot,我一直在阅读有关将字符串转换为整数、atoi和strol C标准库函数以及其他一些我似乎无法理解的事情 我最初尝试做的是从字符串中获取一系列数字,并将它们放入int数组中。以下是字符串的片段单个字符串中有多行: getldsscan AngleInDegrees,DistInMM,Intensity,ErrorCodeHEX 0,0,0,8035 1,0,0,8035 2,1228,9,0 3,4560,5,0 ... 230,1587,80,0 231,0,0,8035 232,1653,89

我一直在阅读有关将字符串转换为整数、atoi和strol C标准库函数以及其他一些我似乎无法理解的事情

我最初尝试做的是从字符串中获取一系列数字,并将它们放入int数组中。以下是字符串的片段单个字符串中有多行:

getldsscan
AngleInDegrees,DistInMM,Intensity,ErrorCodeHEX
0,0,0,8035
1,0,0,8035
2,1228,9,0
3,4560,5,0
...
230,1587,80,0
231,0,0,8035
232,1653,89,0
233,1690,105,0
234,0,0,8035
...
358,0,0,8035
359,0,0,8035
ROTATION_SPEED,4.99
输出来自我的真空机器人Neato XV-21。我已经通过COM端口连接获得了上面的输出,并且当前已将其存储在字符串中。因为机器人可以输出各种不同的东西。在这个例子中,我从一个字符串neatoOutput读取数据,该字符串包含了在我从机器人的激光扫描仪请求更新后机器人的输出

getldsscan是我发送给机器人的命令,当我得到COM输出时,它被读回,所以我们跳过它。下一行只是关于输出的每个值的有用信息,可以跳过它。从那时起,输出有趣的数据

我试图得到每行数据中第二个数字的值。该数字是扫描仪到障碍物的距离。我想要一个整洁的int-distance数组[360],其中包含从机器人返回的所有距离值。机器人将输出360个距离值

我还没有对错误检查或读取每行数据中的其他值感到烦恼,因为我将在稍后了解如何提取所需的当前基本数据后获取它们。到目前为止,我可以使用类似于:

int startIndex = 2 + neatoOutput.find("X",0); //Step past end of line character
所以startIndex应该给我数据起始位置的字符索引,但正如上面的例子所示,每个数字的值的大小范围从单个字符到4个字符。因此,简单地在字符串中向前移动一个设置的数量是不起作用的

我想做的是

neatoOutput.find("\n",startIndex );
如果代码多一点,我应该能够一次解析一行。但我仍然很困惑,我该如何提取我想要的第二个数字

如果有人对入侵/编码机器人感兴趣,您可以转到:-

更新:已解决

谢谢大家的帮助,下面是我近期将要使用的代码。您会注意到,我最终不需要知道我认为需要使用的int startIndex变量

//This is to check that we got data back
signed int dataValidCheck = neatoOutput.find("AngleInDegrees",0);
if (dataValidCheck == -1)
    return;

istringstream iss(neatoOutput);
int angle, distance, intensity, errorCode;
string line;

//Read each line one by one, check to see if its a line that contains distance data
while (getline(iss,line))
{
    if (line == "getldsscan\r")
        continue;
    if (line == "AngleInDegrees,DistInMM,Intensity,ErrorCodeHEX\r")
        continue;

    sscanf(line.c_str(),"%d,%d,%d,%d",&angle,&distance,&intensity,&errorCode); //TODO: Add error checking!
    distanceArray[angle] = distance;
}

尝试这个未经测试的方法,因此可能会出现一些小错误:

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

int main()
{
    string s("3,2,6,4\n2,3,4,5\n");
    istringstream iss(s);
    int a, b, c, d;
    string line;
    while (getline(iss,line))
    {
        // Method 1: Using C
        sscanf(line.c_str(),"%d,%d,%d,%d",&a,&b,&c,&d);


        // Method 2: Using C++
        std::stringstream  lineStream(line);
        char  comma;
        lineStream >> a >> comma >> b >> comma >> c >> comma >> d;


        // do whatever
    }

}

尝试这个未经测试的方法,因此可能会出现一些小错误:

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

int main()
{
    string s("3,2,6,4\n2,3,4,5\n");
    istringstream iss(s);
    int a, b, c, d;
    string line;
    while (getline(iss,line))
    {
        // Method 1: Using C
        sscanf(line.c_str(),"%d,%d,%d,%d",&a,&b,&c,&d);


        // Method 2: Using C++
        std::stringstream  lineStream(line);
        char  comma;
        lineStream >> a >> comma >> b >> comma >> c >> comma >> d;


        // do whatever
    }

}

您可以自己解析字符串。很简单

代码:


您可以自己解析字符串。很简单

代码:


您应该使用SSCANF的返回值您应该使用SSCANF的返回值我认为您的for循环条件需要修改。第一个循环超过数字isdigit true会导致另一个循环,第二个循环超过非数字!isdigit true会导致另一个循环。另外,两个for循环都将空终止符视为继续循环的理由*p或*p=='\0'再次显示循环。我认为需要修改for循环条件。第一个循环超过数字isdigit true会导致另一个循环,第二个循环超过非数字!isdigit true会导致另一个循环。另外,两个for循环都将空终止符视为继续循环的理由*p或*p=='\0'再次显示循环。