2011-05-29 49 views
0

我試圖解決K & R練習(7.7)。它要求編寫一個程序,它將文件名作爲參數並搜索它們以查找特定模式。對於模式匹配,我使用滑動窗口的方法,即檢查前n個字符的匹配,然後將「窗口」(我使用數組)右移一個位置,然後再次檢查,直到EOF.I相信我沒有正確使用fseek我做錯了嗎?問題定位FILE *與fseek

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

int pattern_check(FILE *); 

char *pattern="dog"; 

int 
main(int argc,char **argv) 
{ 
    FILE *fp; 
    char *file_name; 
    int i; 
    int matchings; 

    for(i=1;i<argc;i++){ 
     file_name=strdup(argv[i]); 
     fp=fopen(file_name,"r"); 
     if((matchings=pattern_check(fp))){ 
      printf("%d patterns found in %s\n",matchings,argv[i]); 
     } 
     fclose(fp); 


    } 
    system(sleep(10000)); 
    return 0; 
} 

int 
pattern_check(FILE *fp) 
{ 
    int length=strlen(pattern); 
    char window[length]; 
    int i,c; 
    int found=0; 
    unsigned position=ftell(fp); 


    window[length]='\0'; 
    while(1){ 
     /*load characters from file to string*/ 
     for(i=0;i<length;i++){ 
      fscanf(fp,"%c",&c); 
      window[i]=c; 
     } 
     /*compare*/ 
     if(strcmp(window,pattern)==0) 
      found++; 
     if(feof(fp)) 
      break; 
     /*move window one to the right*/ 
     fseek(fp,0,position); 
     position+=1; 

    } 
    return found; 
} 

在此先感謝。

+0

您應該更改pattern_check中的窗口聲明以保存另一個char:char窗口[length +1] ;.否則,window [length] = 0;將無法正常工作。 – Baltasarq 2011-05-29 09:18:41

+0

您正在使用feof。如果你的文件長度爲零,你將調用scanf長度時間把垃圾放入窗口,然後strcmp垃圾。您需要檢查scanf的返回值以決定何時停止讀取文件。 (更好的是,使用fgetc而不是scanf)。直到讀取調用指示錯誤或文件結束後,才能使用feof或ferror。 feof的目的是確定返回零的fread意味着「沒有更多數據」或「錯誤」。 – 2011-05-29 13:16:12

回答

6
fseek (fp, 0, position); 

肯定是錯誤的,參數fseek應該是:

  • 文件句柄。
  • 的位置。
  • 「whence」(從哪裏計算位置)。

換句話說,它應該是:

fseek (fp, position, SEEK_SET); 

而且,順便說一句,你通常應該經常檢查從中可以失敗函數的返回代碼,即使你不認爲它會發生。根據當前的標準,您可能需要製作position a long int。它可能不會對小文件產生任何明顯的區別,但是一旦開始處理大於正常整數可以處理的文件,就會遇到麻煩。

+0

你不會相信我花了多少時間來調試它。我認爲我已經完全掌握了光標位置,類型大小以及涉及的所有內容的跟蹤。所有問題都以切換順序歸結爲幾個參數。歡迎來到編碼 – NicoBerrogorry 2017-12-06 22:47:14

2

fseek()的參數是向後?