C-scanf仅在特定的字符序列之后提取引号中的数字

C-scanf仅在特定的字符序列之后提取引号中的数字,c,scanf,stdio,C,Scanf,Stdio,假设我有这样一个字符串: Hello World - this is a line of textCOLOR="4" 该字符串存储在buf[1000] 如您所见,此字符串有一个颜色标记,格式为color=“n”。该数字是需要提取的(可以在1到56之间)并分配给int变量的数字。我希望这个标签能够在字符串中的任何位置 我可以运行以下代码来提取颜色值: int colorNumber = 1; //default value if (scanf(buf, "%*[^\"]\"%2d[^\"]\""

假设我有这样一个字符串:

Hello World - this is a line of textCOLOR="4"
该字符串存储在
buf[1000]

如您所见,此字符串有一个颜色标记,格式为
color=“n”
。该数字是需要提取的(可以在1到56之间)并分配给
int
变量的数字。我希望这个标签能够在字符串中的任何位置

我可以运行以下代码来提取颜色值:

int colorNumber = 1; //default value
if (scanf(buf, "%*[^\"]\"%2d[^\"]\"", &colorNumber)) {
    // work with number
}
这很好,但是如果字符串中包含数字或引号,那么scanf将无法生成数字

我尝试了我的第二个scanf论点的一些变体,但这些都不起作用。我尝试了
“%*[^\”]COLOR=\%2d[^\“]\”“
,但这似乎根本不起作用

我已经浏览了scanf的手册页,但是我也找不到我在里面要找的东西

也许scanf不是适合这个应用的工具?如有必要,我愿意尝试其他库/函数。

试试

if (sscanf(buf, "%*[^C]COLOR=\"%d", &colorNUM) == 1)
您尝试的
“%*[^\“]COLOR”
…格式不起作用的原因是
%*[\”]
匹配到
,跳过颜色,因此将无法匹配颜色。但是,如果在
COLOR
之前的字符串中还有另一个
C
som,则上述操作将失败。为了避免这种情况,最好使用
strstr
,如果
COLOR
可能出现在多个位置,则可能会出现循环

for (const char *p = buf; p = strstr(p, "COLOR"); ++p) {
    if (sscanf(p, "COLOR=\"%d", &colorNum) == 1) {
        // found a color number
另外请注意,尝试匹配
%d
后面的字符是毫无意义的,因为无论它们是否匹配,返回的值都是相同的,因此无法判断。如果要确保数字后面有一个
,则需要

int end = 0;
if (sscanf(p, "COLOR=\"%d\"%n", &colorNum, &end), end > 0)

通过检查<代码> %n/COD>写入“代码>结束<代码>,您也检查所有的代码在<代码> %n/COD>正确匹配。

您应该考虑使用<代码> STRSTR < /代码>查找“颜色”关键字;如果找到它,您可以从该过程中处理。Scanf不是正则表达式。不能只是<代码> ATOI(Strut(BUF)”COLOR=\”“)+7)或类似的东西?@Kamil我想你少了一个
@KamilCuk这真的很好用,谢谢!我注意到它也适用于两位数:)谢谢你花时间回答这个问题,克里斯。你的解决方案比我想做的更有意义。我想我可能让事情变得更难了。