【问题标题】:Replacing lines in a text file with C用 C 替换文本文件中的行
【发布时间】:2018-03-06 13:15:14
【问题描述】:

我有一个需要更改的配置文件。

文件的结构是:

resolution 12x34
interval 1234

所以两个带有空格分隔符的字符串。我用来改变它的代码是这样的:

FILE *fp = fopen(configuration_file, "a+");
char str[100], key[100], value[100];
if(fp) {
    while(fgets(str, 100, fp) != NULL) {
        if(2 == sscanf(str, "%s %s", &key, &value)) {
            if(strcmp(key, "resolution") == 0){
                if(msg->resolution){
                    fprintf(fp, "%s %s\r\n", key, msg->resolution);
                }
            } else if(strcmp(key, "interval") == 0) {
                if(msg->interval) {
                    fprintf(fp, "%s %d\r\n", key, msg->interval);
                }
            } else {
                fputs(str, fp);
            } 
        } else {
            fputs(str, fp);
        }
    }
} else {
    (void)printf("-- Configuration file not found (%s)\r\n --", configuration_file);
}
fclose(fp);

我们的想法是逐行阅读。根据fgets 的文档,它说它停在换行符处。字符串扫描每一行并将它们解析为键和值。到目前为止一切顺利,按预期行事。然后将新行打印到文件中,覆盖它刚刚扫描的行。这就是问题所在。如果我使用fprintf,则只处理第一个值,即分辨率。结果是:

resolution oldxres
resolution newxres

它会覆盖错误的行并完全跳过第二行。

如果我删除 fprintf 而只是打印它找到的值,它会按预期打印两者。

我在这里缺少什么? fprintf 是否推送文件指针?

【问题讨论】:

  • a+rw 不同。还有更多错误。
  • fgets 之后,您必须(当然!)将文件指针倒回到行首。
  • 当然,新行也必须与旧行完全相同长度相同。所以用123x456 替换12x34 永远不会起作用,因为它会覆盖下一行的开头
  • @PaulOgilvie 感谢您的建议。不知道您必须倒回文件指针,或者行的长度必须完全相同。

标签: c printf scanf fgets


【解决方案1】:

然后将新行打印到文件中,覆盖刚刚扫描的行。

文件不能以这种方式工作。写入新文件。完成后,将新文件重命名为旧名称。或者,将整个文件读入内存,更改内存中的内容,然后将其写回。

如果修改后的行永远不会比原始行长,您可以重写单个行。否则,修改后的行将溢出您尚未阅读的下一行,并将其销毁。为了防止这种情况,您需要某种前瞻缓冲区,这太麻烦且容易出错。在最坏的情况下,您无论如何都需要阅读整个文件。

【讨论】:

  • 没想到修改后的行长,后来觉得有点傻。不是一个好方法。感谢您的建议。像魅力一样工作!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-06-07
  • 1970-01-01
  • 2016-08-08
  • 1970-01-01
  • 2015-09-22
  • 2012-03-19
  • 2017-06-06
相关资源
最近更新 更多