繁体   English   中英

在C ++中分割字串

[英]Splitting String in C++

我想要的是:

要解析一个MAC地址字符串并获得六个uint8_t值的数组,其输入类似于string str = "01:23:45:AB:CD:EF";

我尝试过的方法(无效):

sscanf(str.c_str(), "%x:%x:%x:%x:%x:%x", &mac[0], &mac[1], &mac[2], &mac[3], &mac[4], &mac[5]);

为什么不起作用:我正在Arduino IDE的帮助下为ESP8266 Wi-Fi模块编程。 即使Arduino开发板的官方核心支持sscanf() ,ESP8266的核心也不支持。 nicjohnston所述, 无法解决 GitHub上给出的问题的解决方案 。)

最不推荐:

占用过多RAM,CPU周期或程序存储空间的任何内容。
同样,某些使用sscanfsetjmplongjmp或直接或间接依赖于sscanfsetjmplongjmp (以及其他几个东西)可能不起作用。

编辑:下面@ms的答案是绝对正确的,但是我意识到在设计自己的代码之后(如下所示)。

for(uint8_t i=0; i<5; i++)
  mac[i]=strtol(Serial.readStringUntil(':').c_str(),NULL,16);
mac[6]=strtol(Serial.readStringUntil('\n').c_str(),NULL,16);

您可以使用正则表达式提取内容并将其存储在数组中。 然后解析该数组以获得相应的uint8_t等效项。

正则表达式可能像: [0-9A-F][0-9A-F]

您可以参考此参考链接以获取有关正则表达式及其使用方法的更多详细信息: http : //www.cplusplus.com/reference/regex/regex_search/

在C ++中, regex_search允许搜索regex模式,并可能还提取搜索(或匹配)的模式。

在您的特定用例中,您可以简单地遍历字符串并将十六进制子字符串转换为数字,如下所示:

  • 每个子字符串均由两个十六进制字符组成; 让子字符串用XY表示
  • XY[0-9][AF] ,其中A 表示 10B表示11等(十进制)
  • 从ASCII值到这些字符之一的数字含义的转换取决于char来自哪个字符集:

  • 如果char c来自[0-9] ,则其十进制含义为c-'0' ,即减去偏移量,以便以下映射应用'0'=>0, '1' => 1, ...

  • 如果char c来自[AF] ,则映射可以表示为c-'A'+10

  • 然后,每个子字符串XY十进制数字v的计算如下: v=X*16 + Y

  • 子字符串由单个字符分隔(此处为: ,但这无关紧要)

以下代码实现了这些想法:


#include <string>
#include <cstdlib>

std::uint8_t getNum(char hexChar)
{
    if(hexChar >= '0' && hexChar <= '9')
    {
        return hexChar - '0';
    }
    return (hexChar-'A'+10);
}

int main()
{
    std::uint8_t mac[6];
    std::string str = "01:23:45:AB:CD:EF";

    std::uint8_t j = 0;
    for(std::uint8_t i = 0; i<6; ++i)
    {
        mac[i] = getNum(str[j])*16 + getNum(str[j+1]);
        j+=3; // get to the next substring
    }
}

我来晚了,女士的回答是正确的。

我的答案有点不同,因为它使用来从字符串中计算十六进制,并使它更接近c ++ 11。 虽然我不确定您的ESP8266模块是否支持它,但希望对您有所帮助。

#include <string>
#include <array>

std::array< uint8_t, 6> MAC_fromStringToArray(const std::string& str)
{
    std::array< uint8_t, 6> ret ;

    for (auto i = 0; i < 6; i++)
    {
        ret[i] = std::stoi(str.substr((i * 3), 2), nullptr, 16);
    }

    return ret;
}

int main()
{
    std::string str = "01:23:45:AB:CD:EF";

    std::array< uint8_t, 6> mac = MAC_fromStringToArray(str);

    return 0;
}

编辑:由于似乎不可用,我将其更改为传统数组。

uint8_t * MAC_fromStringToArray(const std::string& str, uint8_t arr[])
{
    for (int i = 0; i < 6; i++)
    {
        arr[i] = std::stoi(str.substr((i * 3), 2), nullptr, 16);
    }

    return arr;
}

需要以不同的方式调用它:

uint8_t arr[6]; 

MAC_fromStringToArray(str, arr);

希望有帮助,恐怕如果无法使用与您相同的编译器,很难解决您的情况。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM