我正在编写一个C程序来解析一些可能有两个不同版本的输入文件。我需要能够在解析文件时推断出文件格式。
第一个版本只是一个数字列表,每行一个:
123
456
789
第二种类型的文件每行有两个数字,顶部有一行标记为文件格式的最新版本
#version 2
123 10
456 20
789 30
最简单测试它的方式我正在阅读的文件以"#version N"
行开头?如果版本行在那里我想要使用它,如果不是,那么我不想使用输入流中的任何字符。
问题在于我认为我需要一些未读取字符的方法,我只知道ungetc,它只适用于单个字符,而不适用于整行。
答案 0 :(得分:2)
我不确定我理解你的问题。看起来你需要的只是ungetc()
,因为你可以跳过空格直到你看到一个数字或#
,然后你会知道哪个文件是哪个。但是你觉得你需要更多,我不知道你为什么这么想。
您可以编写一个“标记生成器”,将输入解析为标记,然后使您的处理代码使用标记。然后你可以通过再次查看第一个标记指针来“回放”。
这是一个很好的分工:你可以让你的标记器处理跳过空格,跳过注释,甚至可以处理像#include
指令这样的事情。您可以读取一行,让令牌器将其拆分为空白区域,并将指针传递给该行中的每个单词以供其余代码使用。
如果您希望程序尽可能灵活,可以使用malloc()
为输入中的每个标记分配缓冲区。我已经用这种方式编写了简单的编译器,因为我希望能够在令牌级别“回放”以查看其他内容之前的内容。输入文件被转换为令牌的链接列表,我能够在当前令牌之前和之后查看,以尝试从上下文中解决问题。
答案 1 :(得分:1)
读取文件后,您可以将指针设置回原始位置。
C提供fseek
来更改文件指针的位置。一旦您读取文件并发现它的版本不同,您可以使用fseek
将指针设置为开头,以便下一次读取从文件的开头开始。
答案 2 :(得分:0)
好吧,如果您知道每个文本文件将在文件顶部有#version x
(其中x是数字)。您可以使用简单的fscanf来确定版本号,然后调用函数来处理该类型的版本:
/* where 'str' is a char[] and 'version' is an int */
fscanf(pfile, "%s %d", str, &version)
if (version == 1) {
/* Handle version 1 */
}
if (version == 2) {
/* Handle version 2 */
}