【问题标题】:Deleting specific lines in a file in C在C中删除文件中的特定行
【发布时间】:2015-01-14 15:09:33
【问题描述】:

当前删除部分代码。

printf("Opening input and output file... ");
    if ((ifp = fopen("baza.txt", "r")) == NULL){
        fprintf(stderr, "Error! input file open error.");
        exit(1);
    }
    if ((ofp = fopen("baza.txt", "w")) == NULL){
        fprintf(stderr, "Error! output file open error");
        exit(1);
    }
printf("OK\n");
printf("Updating file... ");
    rewind(ofp);            
    rewind(ifp);            
    i = 0;
    while (!feof(ifp)){
        if (ftell(ifp) == point[i]){
            i++;
            for (s = 0; s < 5; s++)
                fgets(buffer, 30, ifp);
        }
        fgets(buffer, 30, ifp);
        fputs(buffer, ofp); fputs("\n", baza);
    }
printf("OK\n");
printf("Closing input and output files... ");
    rewind(ifp);
    rewind(ofp);
    fclose(ifp);
    fclose(ofp);
printf("OK\n");

文本文件:

Samsung
Galaxy Mini 2
250
14
-
HTC
One X
350
25
-
Sony
XPERIA
300
9
-
HUAWEI
Ascend Y530
116
9
-

首先要弄清楚几件事。已经有一部分代码找到了特定的输入(因为这是一个“移动商店”控制台应用程序,用户可以搜索商店中当前商品的开发者、型号、价格或数量,然后在每个电话信息'-'。

假设用户正在搜索移动价格 350,它将跳转到第一个价格,比较,仅 5 行,比较等。如果找到正确的值,它会在其上方存储“-”的位置(第一项的特殊情况,因为它只有一个空格而不是 '-'。直到现在都可以正常工作,这就是我没有包含该代码的原因。

当我尝试从库中删除某部手机时,问题就开始了。我想到的是它以 2 种模式打开文件,读取和写入,并倒回开始(以防万一)。现在因为“baza.txt”文件由于在 w (ofp) 中打开而为空,但它仍然包含在 ifp - r 中,所以我洗牌 ifp 文件并将所有内容导入到 ofp,除非指针到达点的数组位置.

->我遇到的唯一问题是,当我打开这个文本文件时,我只能找到前一个文件的最后一行。看起来它不断地在第一行绘制文本,从不跳到第二行。在 a+ 模式下这工作正常,但问题是在 a+ 模式下它不会删除内容,在文件中留下一团糟——重复、剩余等,因为文件被缩小了。

我也尝试在打开它时立即关闭它(因为它现在是一个空文件)并在 a+ 中打开它,但编译器显然不喜欢这样。

抱歉,帖子太长了

Tl/博士。阅读上面的->

【问题讨论】:

  • 为什么要使用文本文件来处理这类事情?为什么没有合适的数据库?
  • 因为这是大学作业,我必须使用文本文件 :) 我同意这毫无意义。

标签: c file input


【解决方案1】:

您不能单独打开同一个文件进行读写,第二次fopen 调用将截断文件,因此您将丢失所有内容。

处理您的情况的常用方法是写入临时文件,完成后将临时文件重命名为原始文件。

作为旁注,不要使用while (!feof(...)),它在大多数情况下不会像您期望的那样工作,因为文件结束标志直到之后才会设置 您尝试从文件末尾以外的地方读取,并且您将重复循环一次。相反,例如while (fgets(...) != NULL).

【讨论】:

  • 修复它的一种方法是打开文件进行读取,取消链接/删除它,然后打开它进行写入。这样您就可以继续阅读旧内容,直到您关闭ifp,因为输出将是位于磁盘其他位置的全新文件。大多数人仍然使用临时文件,因为这样您的文件不会在出现错误时被破坏。
  • 是的,我去找临时文件只是为了看看我是否会得到与之前相同的响应(仅最后一行),但结果非常好。现在我将它写入 temp-baza.txt 然后将其传输回 baza.txt ......但我很感兴趣,文件不是在 r 模式下“维持”自身吗?或者如果 w 中的文件被覆盖,它也会被删除吗?不管怎样,谢谢大家的帮助! :)
【解决方案2】:

永远不要在w+ 模式下打开要从中读取的文件,因为在读取之前会截断它。充其量您可以保留系统或库放入缓存中的内容,但这是未充分终止的行为。

当你在阅读之前倒回ofp文件时,你应该在a+模式下打开它,但是r+会更好,因为它给出了最初定位在文件开头的指针。要解决文件末尾的垃圾问题,您只需在关闭它之前在当前偏移处截断ofp,当然不要倒带!

你的程序的结尾应该是:

printf("OK\n");
printf("Closing input and output files... ");
    off_t offset = ftell(ofp);
    ftruncate(ofp, offset);
    /* rewind(ifp); useless
    rewind(ofp); */
    fclose(ifp);
    fclose(ofp);
printf("OK\n");

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-03-27
    • 1970-01-01
    • 1970-01-01
    • 2020-08-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多