2016-04-10 5 views
1

私はコードを書いたが、なぜ最後のprintfが予期せぬ結果をもたらすのか分からない。私のコマンドライン引数は、次のようにコードは12と15だった:なぜinet_ntoaがprintfで2回呼び出されたのが間違った出力ですか?

#include <stdio.h> 
#include <netinet/in.h> 
#include <arpa/inet.h> 

int main(int argc, char *argv[]) 
{ 
    struct in_addr adr, adr2; 
    int num, num2; 

    num = atoi(argv[1]); 
    num2 = atoi(argv[2]); 

    adr.s_addr = htonl(num); 
    adr2.s_addr = htonl(num2); 

    printf("%x %x\n", num, adr.s_addr); # c c000000 
    printf("%x %x\n", num2, adr2.s_addr); # f f000000 

    printf("%s\n", inet_ntoa(adr)); # 0.0.0.12 
    printf("%s\n", inet_ntoa(adr2)); # 0.0.0.15 
    printf("%s %s\n", inet_ntoa(adr), inet_ntoa(adr2)); # 0.0.0.12 0.0.0.12 
    return(0); 
} 

私は最終的な出力は「0.0.0.12 0.0.0.15」であることを期待しかし、それはそうではありません。誰も助けてくれませんか?

答えて

3

inet_ntoa関数は、静的バッファへのポインタを返します。この場合、関数は別の関数のパラメータとして2回呼び出されます。関数のパラメータの評価の順序は未定義であるため、スタティックバッファの内容は最後に実行されたものになります。常に同じバッファを返すので、同じものが2回印刷されます。

だからあなたは、介在配列ポイントなしで、よりその一度、すなわち、別の文、短いなど&&||などの回路演算子、コンマ演算子、または三項演算子をこのような関数を呼び出すことはできません。

この特定のコードの場合、への1回の呼び出しで、それぞれprintfへの2回の個別の呼び出しがこれを行う正しい方法です。

また、この関数の結果を保存する予定がある場合は、ポインターを保存するだけでは意味がありません。inet_ntoaが呼び出されるたびにポインターのデータが変更されるためです。 strcpyまたはstrdupを使用してコピーする必要があります。

+0

ありがとうございました。それは助けになった。 – anupamb

関連する問題