2013-03-16 13 views
0

我知道什麼是分割錯誤,我不需要知道它的定義:) 我只需要知道它來自我的代碼。該程序旨在將單詞作爲輸入,從文本文件中讀取,寫入單獨的文本文件,然後打印讀取文件和輸入中的所有單詞。C分割錯誤中的文件I/O

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

int main(int argc, char*argv[]){ 
    FILE *read; 
    FILE *write; 
    char **list=malloc(sizeof(char*)); 
    char **oldlist=malloc(sizeof(char*)); 
    char *oldword=malloc(sizeof(char)); 
    char exit[]="end"; 
    int a, c, r=0, w=0, n=0, z= 0, y=0, d=0, g=0; 

//check arg 
for(a=0; a<argc; a++){ 
    if(strcmp(argv[a], "-r")==0){ 
     r =1; 
     read=fopen("read.txt", "r"); 
    } 
    else if(strcmp(argv[a], "-w")==0){ 
     w =1; 
     write=fopen("write.txt", "w"); 
    } 
} 
if(r==0 && w==0){ 
    printf("Error: Invalid Command.\n"); 
} 
printf("Read = %d | Write = %d\n", r, w); 

//getwords 
printf("Enter your words: "); 
while(1){ 
char *word=malloc(sizeof(char)); 
list=realloc(list, sizeof(char*)*(z+10)); 
word=realloc(word, sizeof(char)*(z+10)); 
scanf("%s", word); 
       if (strcmp(word,exit)==0){ 
     break; 
       } 
       else{ 
       *(list+z) = word; 
      z++; 
      } 
} 

//read 
if (r==1){ 
    do{ 
     while(1){ 
      *(oldword+d)=fgetc(read); 
      d++; 
     } 
    }while(feof(read) != 0);    
} 
*(oldword+(d-1))="\0"; 

printf("Your words are:\n"); 
      puts(oldword); 
    for(c=0; c<n; c++){ 
      puts(*(list+c)); 
    } 

    //write 
    if (w ==1){ 
     if(w==1){ 
      fputs(*(oldlist+c),write); 
     } 
    for(c=0; c<n; c++){ 
      fputs(*(list+c),write); 
     } 
    } 
    //end 
    free(list); 
    fclose(read); 
    fclose(write);   
    return 0; 

} 
+0

不要問這樣的問題。如果您遇到段錯誤,請告訴我們您代碼的哪一行,或者您只是在浪費我們的時間。 – 2013-03-16 14:47:44

回答

2

如果您編譯與(g標誌),調試和運行下的valgrind它應該給你的,爲什麼它賽格故障的非常好的跡象。

3

您的字分配1個字節:

char *word=malloc(sizeof(char)); 

然後你讀一個字符串到它。這是一個緩衝區溢出,並導致很大的不快(和Stack Overflow這樣的問題)。具體來說,讀長字會踐踏'堆'(由malloc()等控制的數據空間)中的控制信息以及用於確定哪些空間可用而哪些不可用的加擾數據。什麼構成「長字」取決於系統;從技術上講,除了空字符串(只是一個終端'\0')之外的任何字符串都太長了,但如果單詞不超過7個字節,則可能會因藍色謀殺而逃脫。


但不應該realloc的照顧內存的問題?我試圖使字符串輸入無限。

嗯...這是爲做生意的方式有點奇怪,但wordrealloc()之前你實際使用它可以讓你周圍的一些問題。

具體來說,在循環中第一次溢出內存分配word之前,您可以讀取最多9個字符的字符。然而,從使其「無限」,並使其無限是不平凡的是很長的路要走。一個問題是,%s停止以空格字符掃描;從整體上看,這對您有利。另一個是你似乎使用z作爲你輸入的字符串數量的一個計數,也是你輸入的字符串的長度。如果列表增長超過10個條目,則不會重新分配list

你仍然可以遇到各種問題。例如,您對oldword的處理不會執行額外的realloc();它只分配一個字節。然後你有一個完全無限的無限循環(如果它完全被輸入的話)。這個循環是一個災難:

while(1){ 
     *(oldword+d)=fgetc(read); 
     d++; 
    } 
+0

但不應該realloc照顧內存問題?我試圖使字符串輸入無限。 – ploosh 2013-03-16 02:48:38

+0

嗯......作爲一種做生意的方式有點奇怪,但是在實際使用之前''word'的realloc()'會讓你解決一些問題。具體來說,在溢出內存分配「word」之前,可以讀取最多9個字符。然而,從使其「無限」,並使其無限是不平凡的是很長的路要走。一個問題是'%s'停止掃描空白字符;從整體上看,這對您有利。你仍然可能遇到各種問題。例如,您對'oldword'的處理不會執行額外的'realloc()'。 – 2013-03-16 03:18:32