C言語で、関数の可変引数について教えてください。(環境:SH4用Linux)


int  ConsolePrint;
void dprintf(const char *arg, ...)
{
  if (ConsolePrint)
  {
    printf(arg);
  }
  else
  {
    fprintf(stderr, arg);
  }
}

上記の関数を、
dprintf( ”data=[%d]¥n”,10);
で呼び出します。ConsolePrintの値で処理を分けます。

printf の場合は、2つとも引数が渡り、結果の表示は、
data=[10]
となるのですが、
fprintf の場合は、2つめの引数がきちんと渡らず、
data=[1]
等となったりします。
fprintf に可変数の引数を渡すにはどうやればよいのでしょうか?

本当は syslog を使いたいのですが、比較しやすいように fprintf を使いました。

回答の条件
  • URL必須
  • 1人2回まで
  • 登録:
  • 終了:--
※ 有料アンケート・ポイント付き質問機能は2023年2月28日に終了しました。

回答3件)

id:Kumappus No.1

回答回数3784ベストアンサー獲得回数185

ポイント20pt

http://www.die.net/doc/linux/man/man3/fprintf.3.html

fprintf(3): formatted output conversion - Linux man page

vprintf, vfprintfを使ってみました。環境はgcc+x86Linuxです。


#include <stdio.h>

#include <stdlib.h>

#include <stdarg.h>


int ConsolePrint;


void dprintf( const char *arg, ...)

{

char* p;

va_list ap;


va_start( ap, arg );


if (ConsolePrint){

vprintf( arg, ap );

}

else{

vfprintf( stderr, arg, ap );

}

va_end( ap );


}


main( const int argc, char** argv )

{

ConsolePrint = 1;

dprintf(” data = [%d]¥n”, 10 );

ConsolePrint = 0;

dprintf(” data = [%d]¥n”, 10 );

}

id:GigaSlave

なるほど、別の関数を使うのですか。

vprintfでできるんですね。

と言う事は、syslogの場合は、vsyslogと言うのがあるのでこれでいけるのかな。

2005/09/08 18:21:47
id:dev_zer0 No.2

回答回数332ベストアンサー獲得回数25

ポイント20pt

C FAQ 15.5参照

その作り方だとprintf の場合は「たまたま」上手く動いているように見えているだけで、別のコンパイラ、環境では動かない可能性があります。


int  ConsolePrint;

void dprintf(const char *arg, ...)

{

  va_list ap;

  va_start(ap, arg);

  if(ConsolePrint) {

    vprintf(arg, ap)

  } else {

    vfprintf(stderr, arg, ap);

  }

  va_end(ap);

}

id:GigaSlave

ありがとうございます。

なんと、たまたまだったんですか(^^;

質問して良かったです。

2005/09/08 18:25:48
id:aki73ix No.3

回答回数5224ベストアンサー獲得回数27

ポイント20pt

この場合は、va_listを使いましょう

vsprintfで一度展開してやるといいかもしれません


次のようなソースでやりたいことができます


#include <stdarg.h>

#include <stdio.h>


int    ConsolePrint;

void dprintf(const char *arg, ...)

{

  char sctmp[4096];

  va_list ap;

  va_start(ap,arg);

  vsprintf(sctmp,arg,ap);

  va_end(ap);

  if (ConsolePrint)

  {

    printf("%s",sctmp);

  }

  else

  {

    fprintf(stderr,"%s",sctmp);

  }

}

int main(int argc, char* argv[])

{

   int a;

   ConsolePrint=0;

   dprintf("data=[%d]¥n",10);

   ConsolePrint=1;

   dprintf("data=[%d]¥n",10);

   return 0;

}

id:GigaSlave

皆さんありがとうございました。

勉強になりました。

syslogの方も、vsyslogで動作しました。

2005/09/08 18:28:54

コメントはまだありません

この質問への反応(ブックマークコメント)

トラックバック

「あの人に答えてほしい」「この質問はあの人が答えられそう」というときに、回答リクエストを送ってみてましょう。

これ以上回答リクエストを送信することはできません。制限について

回答リクエストを送信したユーザーはいません