簡體   English   中英

如何通過命令行參數傳遞參數來將文本替換到文件的特定位置

[英]How to replace the text into a particular location of a file by passing the argument via command line argument

我的意圖是讀取第一行中的第二個元素,並將其替換為我們作為命令行參數傳遞的值,並將其替換為input.txt文件

輸入文件:logic.txt

一個= 1234

兩個= 3456

我希望在編譯代碼后像這樣更改我的文件。

./a.out 1567

目前我正在得到這樣的輸出

./filelogic 1567

1567 = 1234

兩個= 5678

預期的輸出文件在編譯后應該像這樣修改

邏輯文件

一個= 1567

兩個= 5678

        char buf[MAXSIZE] = {};
        int num = 0;
        int i = 0;

        num = atoi(argv[1]);

        printf("%d",num);

       FILE *fp1;
              fp1 = fopen("logic.txt","r");//currently reading the file.
       if(fp1 != NULL)
       {

                 fseek(fp1,3,0);//Need to Move the pointer to the 3rd position where i need to replace the num(fseek(fp1,??,0))-->how we can achieve that.

                 //Using which method i can replace the num value into a file (means need to replace 1234 inplace of 1567)

               //Once the changes are done need to replace in the same file.

                fread(buf, 1, MAXSIZE, fp1);

                printf("%s\n",buf);

                 fclose(fp1);


       }else {
                printf("Cannot open file"");
                    exit(1);
       }

有人可以指導我解決此問題嗎?

可以 就地替換文件,但實際上不應該這樣做。 如果嘗試替換字符並且不對文件中已有的字符進行精確的一對一替換,則很可能損壞文件。

為了安全地更改文件的內容,請將整個文件的內容讀取到內存中,進行所需的更改,然后截斷當前文件並將新內容寫入截斷的文件。 (如果該文件太大,無法進行內存中操作,請使用一個臨時文件)

您不想使用atoi將字符串"1567"轉換為整數。 你是在一個文件中的二進制文件替換字符 ,而不是整數值,所以用文字工作,而不是。

您的項目很復雜,只希望替換第一個'='符號之后的文本。 它可能位於文件的第一行,也可能不在文件的第一行,因此您將需要一些標志來指示何時找到第一個'='並進行替換。 (一旦替換完成,您可以簡單地中斷讀取循環並關閉文件-但為方便起見,在示例下面輸出所有行)

每次在寫入文件后關閉文件時,都應驗證fclose返回 ,以捕獲任何流錯誤,或上一次寫入時發生的錯誤,直到下一個文件操作時才發現。

考慮到這些警告和注意事項,您可以執行以下操作:

#include <stdio.h>
#include <string.h>

#define MAXSIZE 64          /* max line/buffer size */
#define FNAME "logic.txt"   /* default file name */
#define REPLACE "1567"      /* default replacement text */

int main (int argc, char **argv) {

    char buf[MAXSIZE] = "";         /* line buffer */
    const char *str = argc > 1 ? argv[1] : REPLACE; /* replacement string */
    int replaced = 0;               /* flag indicating replacement made */
    FILE *fp = fopen (FNAME, "r+"); /* open file reading/writing */

    if (!fp) {  /* validate file open for reading/writing */
        perror ("fopen-FNAME");
        return 1;
    }

    while (fgets (buf, MAXSIZE, fp)) {  /* read each line in file */
        if (!replaced) {                /* if replacement not yet made */
            char *p = strchr (buf, '=');    /* search for '=' in line */
            if (p) {                        /* if found */
                size_t plen = 0;            /* var for length to end */
                p++;                        /* advance past '=' sign */
                plen = strlen (p);          /* get length to end  */

                if (plen < strlen (str)) {  /* check avail length */
                    fprintf (stderr, "error: not enough space in line.\n");
                    return 1;
                }
                strcpy (p, str);                    /* copy str to p */
                if (fseek (fp, -plen, SEEK_CUR)) {  /* backup plen chars */
                    perror ("fseek(fp)");
                    return 1;
                }
                fputs (p, fp);  /* overwite contents with replacement */
                replaced = 1;   /* set flag indicating replacement   */
            }                   /* (you can break, and remove output */
        }                       /*  here if not writing to stdout)   */
        fputs (buf, stdout);    /* output lines to stdout (optional) */
    }
    if (fclose (fp) == EOF)     /* always validate close-after-write */
        perror ("fclose-FNAME");

    return 0;
}

使用文件logic.txt作為示例輸入,並根據需要命名可執行文件filelogic ,以上代碼的使用和操作將產生:

logic.txt文件之前

$ cat logic.txt
one=1234

two=3456

使用/輸出示例

$ ./filelogic
one=1567

two=3456

邏輯文件之后

$ cat logic.txt
one=1567

two=3456

再次,這對於學習非常有用,但是在實踐中,請避免對文件進行就地更改,因為無意中文件損壞的風險遠遠大於使用更改編寫新文件的風險。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM