2016-05-20 9 views
-1

私の主な問題は、構造体Itemから印刷すると、s.nameが2回印刷されることです。Printfは同じ配列を2回出力する

コード:

#include <stdio.h> 

struct Item{ 
    char code[5]; 
    char name[40]; 
}; 

int main(){ 
    FILE *f; 
    struct Item s; 

    //Open file 
    f = fopen("ex.txt", "r"); 

    //Read from file 
    fscanf(f, "%5c;%[a-zA-Z ]\n", s.code, s.name); 

    //Print from file 
    printf("%s %s", s.code, s.name); //Main problem here 
    fclose(f); 
} 

入力(ex.txt):

AB011;Hello World 

出力は次のようになります。

AB011 Hello World 

しかし、その代わりに、それはです:

AB011Hello World Hello World 

ここでは何が起こっていますか?

その他の備考:この動作にはfscanfを使用する必要があります。あなたは書式指定子として

"%5c;%[a-zA-Z ]\n" 

を使用しているfscanfへの呼び出しで

+0

gst_fileは何で\0自分を追加しているのですか?あなたが開いたファイルから読むべきではありませんか? –

+0

'%s':引数にはヌルターミネータが必要です。 – BLUEPIXY

+1

@JewelThiefええ、それについて申し訳ありません。ちょうどそれを修正した。 – Steve

答えて

3

。フォーマット指定子の一部の%5cは、5文字を読み取ってs.codeになります。それは終止ヌル文字の余地を残しません。

printfの引数を%sと指定すると、未定義の動作になります。 %sにはnullで終了する文字列が必要です。

codeのサイズを6文字に変更してから、fscanf行の後にヌル文字で終了する必要があります。

#include <stdio.h> 

struct Item{ 

    /// CHANGED HERE 
    char code[6]; 
    char name[40]; 
}; 

int main(){ 
    FILE *f; 
    struct Item s; 

    //Open file 
    f = fopen("ex.txt", "r"); 

    //Read from file 
    fscanf(f, "%5c;%[a-zA-Z ]\n", s.code, s.name); 

    /// CHANGED HERE 
    s.code[5] = '\0'; 

    //Print from file 
    printf("%s %s", s.code, s.name); 
    fclose(f); 
} 
+0

最後にヌル文字を示すために余分なスペースが必要なのですか? – Steve

+1

@Steve、それは正しいです。 –

+0

@R Sahuさて、私はそれを手に入れました。 。 – Steve

2
  1. あなたはcodeサイズが5つの文字を格納している場合\0ターミネータを含む6バイト、である必要があります。

  2. scanfの場合%[5]c - 正確に5文字を読み取り、末尾には\0を追加しません。

1以外の幅が指定された場合、関数は正確に幅文字を読み取り、引数として渡された配列の連続した場所にそれらを格納します。最後にヌル文字は追加されません。

は何をする必要があるエンド

//Read from file 
fscanf(f, "%5c;%[a-zA-Z ]\n", s.code, s.name); 
s.code[5] = '\0'; 
関連する問題