使用带可选空格的sscanf获取格式化输入

使用带可选空格的sscanf获取格式化输入,c,scanf,C,Scanf,我正在尝试从字幕文件(STL格式)读取输入,其中字符串格式为: 1) 00:00:37:09,00:00:39:24,字幕文本。(即带有空格的时间和文本) 相同字幕格式的另一种格式为 2)00:00:31:02,00:00:33:00,字幕文本。(即时间和文本不带空格) 要阅读这一行,我将执行以下操作: sscanf(*buf, "%2d:%2d:%2d:%2d , %2d:%2d:%2d:%2d , %n", &hh1, &mm1, &ss1, &ms1, &a

我正在尝试从字幕文件(STL格式)读取输入,其中字符串格式为:

1)
00:00:37:09,00:00:39:24,字幕文本。
(即带有空格的时间和文本)

相同字幕格式的另一种格式为

2)
00:00:31:02,00:00:33:00,字幕文本。
(即时间和文本不带空格)

要阅读这一行,我将执行以下操作:

sscanf(*buf, "%2d:%2d:%2d:%2d , %2d:%2d:%2d:%2d , %n",
&hh1, &mm1, &ss1, &ms1, &hh2, &mm2, &ss2, &ms2, &len)

但是,如果字幕文件混合了1)和2)或者该文件包含其他一些空白组合,则会读取错误的文本。如何读取输入以忽略空白

假设
buf
char**buf
上的一个变量(指向
char
的双指针),只要您的“毫秒”字段(通过使用
&ms1
&ms2
作为变量名推断)不超过2位,代码就应该是正常的。格式字符串中显式出现的空白表示“可选空白”。在
%2d
之前,它在技术上是多余的,但不会造成任何伤害

您的片段有一个开括号和两个闭括号。我认为这意味着您正在以下环境中使用它:

int rc;
if ((rc = sscanf(…)) != 8)
    …oops — malformatted data…
else
    …pick up subtitle from `(*buf)[len]` onwards…
如果您遇到问题,则需要显示导致问题的数据。您可以将其打印在我在伪代码片段中编写的
oops-格式错误的数据
处:

if ((rc = sscanf(…)) != 8)
{
    fprintf(stderr, "Malformatted data (rc = %d): <<%s>>\n", rc, *buf);
}
else
{
    …pick up subtitle from `(*buf)[len]` onwards…
}
输出:

00:00:37.09 - 00:00:39.24 = [Subtitle Text 1]
00:00:31.02 - 00:00:33.00 = [Subtitle Text 2]

正如上面的回答中所述,最好总是展示完整的代码,以及您正在使用的操作系统和devkit,因为可能存在差异。我在Linux上使用标准cc编译器尝试了您的代码,没有发现任何错误会稍微引发输入字符串(我删除了buf之前的*before,因为我认为它不是任何间接寻址)

但我的建议是:
如果您无法控制确切的输入格式,请不要使用sscanf()!至少如果您希望创建一个稳定的应用程序。

似乎没有问题。谢谢你的回答。我对可选的空格有点困惑。但现在很清楚:)我也有一个疑问..为什么len不算在rc中?因为C89/C90标准说它不算。没有比这更好或更糟糕的理由了。我想,如果在解析过程中达到了它,它“不会失败”,因此告诉您它成功了并没有多大帮助。OTOH,假设您有一个格式
%s x%n”
,了解
x
是否被读取会很有帮助…我明白了。谢谢您的回答!
00:00:37.09 - 00:00:39.24 = [Subtitle Text 1]
00:00:31.02 - 00:00:33.00 = [Subtitle Text 2]