2016-07-23 75 views
-1

下面的代碼編譯沒有錯誤或警告,我也可以執行程序,它會按預期行事,它會在預期的位置返回錯誤消息,例如提供參數到不存在的文件。這讓我知道代碼工作儘可能線28(關閉!FPC段)調試沒有錯誤或警告

含義必須有從

register int ch, i; 

一個問題之前,向下

return (1); 

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

該程序預計將採取程序名稱本身的命令行參數和兩個文件名s,然後打開這兩個文件,然後應該將字符串從第一個文件複製到第二個文件的最大長度,同時將"添加到新文件中字符串的開頭和結尾。

我的代碼是

fgetline.c

#include "fgetline.h" 

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

    if (argc != 3) { 
     printf("usage: enquote filetocopy filetowrite \n"); 
     exit(1); 
    } 

    fp = fopen(argv[1], "r"); 
    if (!fp) { 
     printf("Couldn't open copy file: (%d) %s\n", errno, strerror(errno)); 
     return -1; 
    } 

    fpc = fopen(argv[2], "r+"); 
    if (!fpc) { 
     printf("Couldn't open write file: (%d) %s\n", errno, strerror(errno)); 
     return -1; 
    } 

    register int ch, i; 

    ch = getc(fp); 
    if (ch == EOF) 
     return -1; 

    i = 0; 
    while (ch != '\n' && ch != EOF && i < max) { 
     line[i++] = ch; 
     ch = getc(fp); 
    } 
    line[i] = '\0'; 

    while (ch != '\n' && ch != EOF) { 
     ch = getc(fp); 
     i++; 
    } 
    return(i); 

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

    fclose(fp); 
    fclose(fpc); 
    return 0; 
} 

fgetline.h

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

int fgetline(FILE *fp, char *line, int max); 
FILE *fp, *fpc; 
#define max 30 
char line[max + 1]; 

我與

debian:~/uni/Ass0$ gcc fgetline.c -Wall -o enquote 
debian:~/uni/Ass0$ cd/
編譯

測試我所做的就是

debian:~/uni/Ass0$ ./enquote 
usage: enquote filetocopy filetowrite 
debian:~/uni/Ass0$ ./enquote test 
usage: enquote filetocopy filetowrite 
debian:~/uni/Ass0$ ./enquote test frog 
Couldn't open write file: (2) No such file or directory 
debian:~/uni/Ass0$ ./enquote monkey frog 
Couldn't open copy file: (2) No such file or directory 
debian:~/uni/Ass0$ cat test 
ting 
test 
123 

[email protected]:~/uni/Ass0$ cat test2 
[email protected]:~/uni/Ass0$ ./enquote test test2 
[email protected]:~/uni/Ass0$ cat test2 

預期的結果將是,當我運行./enquote測試TEST2,會從testtest2複製

ting 
test 
123 

所以會出現像

"ting" 
"test" 
"123" 

謝謝,不知道要給多少信息。

+3

1)啓用**全部**警告! '-Wall'遠離「全部」2)沒有錯誤/警告不能保證正確的代碼。 3)重新格式化你的代碼。 GNU風格非常80年代。 – Olaf

+0

@Olaf,所有警告的標記是什麼,快速查找出來了--Wextra還有什麼,可以用Wextra試過,還是沒有運氣。 – Ausghostdog

+0

@Ausghostdog我當前設置的是'gcc -pedantic -Wall -Wextra -Wbad-function-cast -Wcast-align -Wdisabled-optimization -Wendif-labels -Winline -Wmissing-prototypes -Wanested-externs -Wshadow -Wstrict-prototypes- Wundef -Wwrite-strings -Wformat = 2 -Wullull-dereference -Winit-self -Whift-negative-value -Wshift-overflow = 2 -Wduplicated-cond -O2'。 – melpomene

回答

3

有許多問題與您的代碼,啓用會發現他們中的一些所有的警告編譯:

  • 聲明全局變量在頭文件中是很好的做法,但不能確定他們那裏。關鍵字extern用於聲明。這些定義屬於C文件。在這種情況下,應將諸如fp,fp1,line之類的變量定義爲局部變量,而不是全局變量。
  • 輸出文件argv[2]應該使用"w"模式打開,"r+"用於更新模式,如果文件不存在將會失敗。更新模式非常棘手和混亂,請避免使用它。
  • 不要使用register關鍵字,現在它已經過時了,因爲編譯器足夠聰明,可以確定如何最好地使用寄存器。
  • 您的while循環將從輸入文件中只讀取2行,將第一行存入line陣列並丟棄第二行。
  • return (i);語句退出程序,沒有執行輸出,函數中的其餘語句完全被忽略(-Wall可能已經發現了這個錯誤)。

您可以通過考慮這個簡化的問題:您在每一行的開頭和'\n'在每行年底前要輸出"。您不需要在內存中緩衝行,這會對行長度施加限制。只要輸出",只要你開始一條線並在結束之前:

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

int main(int argc, char *argv[]) { 
    FILE *fp, *fpc; 
    int ch, last; 

    if (argc != 3) { 
     printf("usage: enquote filetocopy filetowrite\n"); 
     exit(1); 
    } 

    fp = fopen(argv[1], "r"); 
    if (!fp) { 
     fprintf(stderr, "Could not open input file: (%d) %s\n", 
       errno, strerror(errno)); 
     return 2; 
    } 

    fpc = fopen(argv[2], "w"); 
    if (!fpc) { 
     fprintf(stderr, "Could not open output file: (%d) %s\n", 
       errno, strerror(errno)); 
     return 2; 
    } 

    last = '\n'; // we are at the beginning of a line 
    while ((ch = fgetc(fp)) != EOF) { 
     if (last == '\n') { 
      fputc('"', fpc); // " at the beginning of a line 
     } 
     if (ch == '\n') { 
      fputc('"', fpc); // " at the end of a line 
     } 
     fputc(ch, fpc); 
     last = ch; 
    } 
    if (last != '\n') { 
     // special case: file does not end with a \n 
     fputc('"', fpc); // " at the end of a line 
     fputc('\n', fpc); // put a \n at the end of the output file 
    } 

    fclose(fp); 
    fclose(fpc); 
    return 0; 
} 
+0

非常感謝你,也爲了解釋。似乎我還有很長的路要走C. – Ausghostdog

+1

@Aghghostdog:熟練掌握C需要很多工作,但是掌握的技能對其他各種更寬容的語言都很有用。繼續學習,這是值得的! – chqrlie