当我在下面的代码中使用sscanf()时,由于某种原因它占用了整行并将它放在第一个字符串中,我没有看到任何问题。 Msg()的输出就像PatchVersion=1.1.1.5 = °?¦§-
该文件看起来像这样(除了每一行都是一个新行,不确定为什么它在StackOverflow上显示为一个)
PatchVersion=1.1.1.5
ProductName=tf
appID=440
代码:
bool ParseSteamFile()
{
FileHandle_t file;
file = filesystem->Open("steam.inf", "r", "MOD");
if(file)
{
int size = filesystem->Size(file);
char *line = new char[size + 1];
while(!filesystem->EndOfFile(file))
{
char *subLine = filesystem->ReadLine(line, size, file);
if(strstr(subLine, "PatchVersion"))
{
char *name = new char[32];
char *value = new char[32];
sscanf(subLine, "%s=%s", name, value);
Msg("%s = %s\n", name, value);
}
else if(strstr(subLine, "ProductName"))
{
char *name = new char[32];
char *value = new char[32];
sscanf(subLine, "%s=%s", name, value);
Msg("%s = %s\n", name, value);
}
}
return true;
}
else
{
Msg("Failed to find the Steam Information File (steam.inf)\n");
filesystem->Close(file);
return false;
}
filesystem->Close(file);
return false;
}
答案 0 :(得分:4)
一种解决方案是使用(在我看来,未充分利用的)字符组格式说明符:
sscanf(subLine, "%[^=]=%s", name, value);
此外,在依赖它们之前,您应该使用sscanf()
的返回值来验证您确实获得了两个值。
答案 1 :(得分:2)
%s
是“贪婪的”,即它一直在阅读,直到它到达whitspace(或换行符或EOF)。 '='
字符不属于这些字符,因此sscanf
只会继续,匹配第一个%s
的整行。
您可能最好使用(例如)strtok()
或简单的逐字符解析器。
答案 2 :(得分:0)
来自scanf的联机帮助页,关于%s:
匹配一系列非空白字符;下一个指针必须是一个指向字符数组的指针,该指针足够长以容纳输入序列和终止空字符('\ 0'),这是自动添加的。输入字符串在空格或最大字段宽度处停止,以先到者为准。
答案 3 :(得分:0)
%s将读取字符,直到遇到空格。由于在'='符号之前/之后没有空格,因此读取整个字符串。
答案 4 :(得分:0)
你使用数组是非常差的C ++技术。您可以使用流,但如果您坚持使用sscanf和数组,那么至少使用vector来管理您的内存。
您可能会准确打印出subLine中的内容以及Msg所执行的操作。这是你自己的代码,因为我从未听说过FileHandle_t。我知道它有一个返回char *的方法,可能你需要管理它。
正则表达式是boost库的一部分,很快就会出现在标准库中。它们是相当“标准”的,你可以用它来解析你的行。
(如果你有,可以使用boost :: regex或tr1 :: regex,VS2008有它)