scanf格式忽略不相关的字符

时间:2013-05-22 15:58:46

标签: c string-formatting scanf

我写了一个简短的示例代码来说明我的问题

#include <stdio.h>
#include <string.h>

unsigned parseAndCompareDouble(const char* inSTR, const char* inF, const char * expect, const char * outF){
    unsigned e = 0;
    char buffer[2000];
    double a = 0;
    if( 1 != sscanf_s( inSTR, inF, &a, sizeof(double) ) ) e += 1;
    if( (int) strlen(expect) != sprintf_s(buffer, 2000, outF, a) ) e += 1;
    if( 0 != strcmp(expect, buffer) ) e += 1;
    return e;
}

unsigned main( void )
{
    unsigned e = 0;
    const char * universalFormat = "X/%lf";

    e += parseAndCompareDouble("X/100", universalFormat, "X/100", "X/%3.0lf");
    e += parseAndCompareDouble("     X/100\r\n", universalFormat, "X/100", "X/%3.0lf");
    e += parseAndCompareDouble("     X/99\r\n", universalFormat, "X/99", "X/%2.0lf");
    e += parseAndCompareDouble("     X / 99 ", universalFormat, "X/99", "X/%2.0lf");
    e += parseAndCompareDouble("X/99", universalFormat, "X/99", "X/%2.0lf");
    e += parseAndCompareDouble("     \"X/100\"\r\n", universalFormat, "X/100", "X/%3.0lf");  

    if( 0 != e ){ printf( "%2u errors occured\n", e ); }
    else{ printf( "all pass\n", e ); }
    return e;
}

我正在寻找一个允许我的示例夹具通过测试的universalFormat。我试图用%*s来摆弄,但我只是觉得不对。我错过了一些概念。

有人可以提供适合此示例的universalFormat并解释如何到达那里。

1 个答案:

答案 0 :(得分:6)

您可以使用以下格式:

const char * universalFormat = "%*[^/]/%lf";

%*[^/]告诉scanf忽略所有非/的内容。我假设你的sscanf_s函数会理解它,虽然我无法自己验证。 Here's the working program (slightly modified).


Daniel Fischer提请我注意,sscanf_ssprintf_s函数在C标准2011(C11)的附录K中定义。 I raised a question about its relation to conformance.


  

知道"X /"在字符串中对我来说很重要。

您似乎正在尝试使用sscanf来解析自由格式输入,这实际上不是 forte 。如果您愿意更改解析代码,可以使用格式字符串的修改版本来完成此任务:

const char * universalFormat = "%[^/]/%lf";

现在,您需要更新解析代码以读取与%[^/]说明符对应的字符串,然后您可以对其进行一些简单的扫描,以确保它符合您的要求。

char xbuffer[2000];
const char *xp;
/*...*/
if( 2 != sscanf_s( inSTR, inF, xbuffer, sizeof(xbuffer), &a, sizeof(a) ) ) e += 1;
if( (xp = strrchr(xbuffer, 'X')) == 0 || strcspn(xp, "X \t") != 0 ) e += 1;