2014/03/12

Recent entries from same category

  1. RapidJSON や simdjson よりも速いC言語から使えるJSONライブラリ「yyjson」
  2. コメントも扱える高機能な C++ 向け JSON パーサ「jsoncpp」
  3. C++ で flask ライクなウェブサーバ「clask」書いた。
  4. C++ 用 SQLite3 ORM 「sqlite_orm」が便利。
  5. zsh で PATH に相対パスを含んだ場合にコマンドが補完できないのは意図的かどうか。

C言語で可変子引数扱う場合は va_start/va_arg/va_end を使うのだけど... #include <stdio.h>
#include <stdarg.h>

void
foo(int n, ...) {
  va_list list;
  int i;
  va_start(list, n);
  for(i = 0; i < n; i++)
    puts(va_arg(list, char*));
  va_end(list);
}

int
main(int argc, char* argv[]) {
  foo(3"foo""bar""baz");  
  return 0;
}
型が拘束出来ない。なので foo(31"bar""baz");  
こんな呼び出し方が出来てしまうし、コンパイルエラーや警告も出ない。実行時にクラッシュする。
なんか出来ないかなーと思ってマクロの海へ...
#include <stdio.h>
#include <stdarg.h>

void
foo(int n, ...) {
  va_list list;
  int i;
  va_start(list, n);
  for(i = 0; i < n; i++)
    puts(va_arg(list, char*));
  va_end(list);
}

#define bar(...) foo((sizeof((char*[]){__VA_ARGS__})/sizeof(char*)), __VA_ARGS__)

int
main(int argc, char* argv[]) {
  bar("foo""bar""baz");
  return 0;
}
これだと引数の個数指定も要らなくなる。エラーにはならないものの、警告は出るので少しはメリットあるかも。 vaarg.c: In function 'main':
vaarg.c:18:3: warning: initialization makes pointer from integer without a cast [enabled by default]
vaarg.c:18:3: warning: (near initialization for '(anonymous)[0]') [enabled by default]
Posted at by | Edit