2017-12-27 1248 views
0

這個程序應該輸入一個數字並計算學生之間的標記之間的平均值。這個程序只適用於以前的學生,但不適用於以下的程序。我認爲那個fscanf有一個錯誤。任何人都可以幫忙嗎?我不確定如何正確使用fscanf

int main() 
{ 
    FILE *cfPtr; 
    int matricola_in, matricola, nEsami, codEsame, voto; 
    char nome[20], cognome[20]; 
    int i, j, trovato = 0; 
    float somma = 0.0; 

    printf("Inserisci una matricola:\n"); 
    scanf("%d", &matricola_in); 

    if((cfPtr = fopen("studenti.txt", "r")) == NULL) 
     printf("Errore"); 

    while(!feof(cfPtr) || trovato != 1){ 
     fscanf(cfPtr, "%d%s%s%d\n", &matricola, nome, cognome, &nEsami); 
     if(matricola_in == matricola){ 
      trovato = 1; 
      for(i = 0; i < nEsami; i++){ 
       fscanf(cfPtr, "%d%d\n", &codEsame, &voto); 
       somma += voto; 
      } 
      printf("Media: %.1f\n", somma/nEsami); 
     } 
    } 

    fclose(cfPtr); 

    return 0; 
} 

編輯:數據的模樣:

matricola nome cognome n.esami`<eol>` 
(for n.esami-rows)codice esame voto`<eol>` 
... 
+0

添加'studenti.txt'前幾行的hexdump - 嘗試'hexdump -C studenti.txt | head'。這可能會立即向您顯示答案,但無論如何都會對其他人的回答有所幫助。 –

+1

數據是什麼樣的?也許你有一個學生多於或少於兩個名稱組件?你也沒有把總和('somma')設回零。你永遠不想用'feof'控制一個循環,而是檢查'fscanf'的返回值,並且當它處理的字段少於請求的字段時,'feof'會告訴你原因是否到達文件末尾。 –

+0

編輯:數據看起來像:(matricola)(nome)(cognome)(n.esami) n.esami-rows :(codice esame)(voto)... – Teorema

回答

1

尚不清楚,但似乎該文件包含有四個或兩個項目線的組合。
考慮閱讀每一行。使用sscanf將該行解析爲最多四個字符串。根據需要使用sscanf來捕捉線上的整數。如果有兩個項目,則處理它們,如果trovato標誌指示已找到匹配項。如果有四個項目,請查看是否匹配並設置trovato

int main() 
{ 
    FILE *cfPtr; 
    int matricola_in, matricola, nEsami, codEsame, voto; 
    char nome[20], cognome[20]; 
    char temp[4][20]; 
    char line[200]; 
    int result; 
    int i, j, trovato = 0; 
    float somma = 0.0; 

    printf("Inserisci una matricola:\n"); 
    scanf("%d", &matricola_in); 

    if((cfPtr = fopen("studenti.txt", "r")) == NULL) { 
     printf("Errore"); 
     return 0; 
    } 

    while(fgets (line, sizeof line, cfPtr)){//read a line until end of file 
     result = sscanf (line, "%19s%19s%19s%19s", temp[0], temp[1], temp[2], temp[3]);//scan up to four strings 
     if (result == 2) {//the line has two items 
      if (trovato) {// match was found 
       sscanf (temp[0], "%d", &codEsame); 
       sscanf (temp[1], "%d", &voto); 
       somma += voto; 
      } 
     } 
     if (result == 4) {//the line has four items 
      if (trovato) { 
       break;//there was a match so break 
      } 
      sscanf (temp[0], "%d", &matricola); 
      sscanf (temp[3], "%d", &nEsami); 
      if(matricola_in == matricola){//see if there is a match 
       trovato = 1;//set the flag 
      } 
     } 
    } 
    printf("Media: %.1f\n", somma/nEsami);//print results 

    fclose(cfPtr); 

    return 0; 
}