Profile

ys2310

Author:ys2310
2008年春にNew York Cityにあるふる〜い大学を卒業。


Categories


new postings


new comments


new trackbacks


monthly archeive


FC2ブログ 転職
DATE: CATEGORY:スポンサー広告
上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。
| BLOG TOP |
DATE: CATEGORY:C/C++ stdarg.h
可変個数実引数並びアクセスマクロ
va_argマクロ
ヘッダ #include
形 式 型 va_arg(va_list ap, 型);
機 能 その関数呼出しにおける、一つ次の実引数の型および値をもつ式に展開する。仮引数apは、va_startによって初期化されたva_list apと同じでなければならない。次にva_argを呼び出したときに、次の実引数の値が返されるようにapを更新する。仮引数型は、指定された型を示す型名とする。ただし、その型のオブジェクトへのポインタ型が、型の後ろに単に*を置くことによって得られなければならない。次の実引数が実際にはない場合、または型が実際の(既定の実引数拡張に従って拡張された)次の実引数の型と適合しない場合、その動作は定義されない。
返却値 va_startマクロの呼出し後の最初のva_argマクロの呼出し、最終引数によって指定された実引数の次の実引数の値を返す。その後の一連の呼出しは、残りの実引数の値を順番に返す。

[Quote]:http://www.bohyoh.com/CandCPP/C/Library/va_arg.html

| BLOG TOP |
DATE: CATEGORY:C/C++ stdarg.h
可変個数実引数並びアクセスマクロ
va_endマクロ
ヘッダ #include
形 式 void va_end(va_list ap);
機 能 va_list apを初期化したva_startの展開によって参照された可変個数の実引数並びをもつ関数からの正常な復帰を可能にする。処理系は、va_endマクロがapを更新して使用できないようにしてもよい(もう一度va_startを呼び出さない限り)。対応するva_startマクロの呼出しがない場合、またはva_endマクロが復帰の前に呼び出されない場合、その動作は定義されない。
返却値 なし。

[Quote]:http://www.bohyoh.com/CandCPP/C/Library/va_end.html

| BLOG TOP |
DATE: CATEGORY:C/C++ stdarg.h
可変個数実引数並びアクセスマクロ
va_startマクロ
ヘッダ #include
形 式 void va_start(va_list ap, 最終引数);
機 能 本マクロは、名前無しの実引数にアクセスする前に呼び出さなければならない。
以降に行われるva_argおよびva_endの呼出しにそなえてapを初期化する。
仮引数最終引数は、関数定義中の可変個数仮引数並びの最右端の仮引数の識別子、すなわち省略記号,...の直前の識別子とする。仮引数最終引数が次の型として宣言されている場合は、その動作は定義されない。
 □ register記憶域クラス
 □ 関数型
 □ 配列型
 □ 既定の実引数拡張を適用した結果の型と適合しない型
返却値 なし。

[Quote]:http://www.bohyoh.com/CandCPP/C/Library/va_start.html

| BLOG TOP |
DATE: CATEGORY:C/C++ stdarg.h
可変個数の引数の作成
これまで、C言語で用いてきた標準関数の中で
printf()関数やscanf()関数のような汎用的で、特異な関数があります

その機能は以前説明しましたが
しかし、printf()関数のように引数の数が固定でない関数を、私たちはまだ作れません
ここでは引数の数を可変的に受け取れる関数を作成してみましょう

まず、プロトタイプで引数の数は固定ではないことを示します
そのためには3つのピリオドからなる...を用います

void function(第一引数 , ...)

この場合でも、必ず第一引数は固定になります
可変にすることができるのは、第二引数以降になります

これで、可変個の引数を受け取ることができる関数を作成することができました
次に受け取った引数にアクセスする必要があります
可変個の引数にアクセスするには、まずstdarg.hヘッダファイルをインクルードします
そして、このヘッダファイルで定義されているマクロと構造体型を利用します

まず、可変個の引数リストにアクセスを開始するにはva_start()を使用します
必ずこれを最初に行う必要があります

void va_start(va_list リスト , prev);

リストには、引数リストへのポインタを指定します
これは、可変個の引数の情報を保持するための stdarg.h で定義されている標準型です
pervは、最初の可変個数の手前の固定引数を指定します(最後の固定引数)

この時点で va_list 型の変数に、可変引数の情報が格納されます
次に、この va_list 型変数から、順に可変引数の内容を呼び出します
引数リストの値を得るにはva_arg()を使用します

type va_arg(va_list リスト , type);

リストは、va_start()で渡してセットされた va_list 型変数を指定します
type は、引数リストから受け取る値の型を指定します
可変この場合、引数を受け取る時に型チェックはされないため、ここで型を明示します

引数リストは、可変個数の引数の始まり部分にセットされています
そこから、va_arg()が呼び出されるごとに次の引数を返します

最後に、すべての引数を取得したらva_end()でポインタを NULL にリセットします

void va_end(va_list リスト);

リストは、これまでva_start()やva_arg()で引数にアクセスしていた変数です

#include "stdio.h"
#include "stdarg.h"

void dynamicArgument(int , ...);

int main() {
dynamicArgument(4 , 10 , 20 , 30 , 40);
return 0;
}

void dynamicArgument(int arg_num , ...) {
va_list args;
int value , count;

if (arg_num < 1) return;

va_start(args , arg_num);

for (count = 0 ; count < arg_num ; count++) {
value = va_arg(args , int);
printf("第%d引数 = %d\n" , count + 2 , value);
}

va_end(args);
return;
}

ここでは、可変個に引数を受け取る関数 dynamicArgument() を作成しています
この関数は第一引数に引数の個数を、第二引数以降は任意のint型引数を受け取り
第二引数以降で受け取った値を、int型として標準出力に出力します

このように、可変個の引数を受け取った場合
受け取り方も動的になるため、何らかの手段で引数の個数を調べる必要があります
printf()関数などは、フォーマット指定子によって引数リストの個数と型をチェックしていますね

因みに、通常va_arg()、va_start()、va_end()は、関数ではなくマクロとして実装されています

type va_arg( va_list arg_ptr, type );
可変個の引数リストから、カレント引数の値を得ます
カレント引数は、呼び出すごとに次の引数に移行します
ヘッダ - stdarg.h
arg_ptr - 引数リストへのポインタを指定します
type - 取得する値の型を指定します
戻り値 - 現在の引数

void va_start( va_list arg_ptr, prev_param );
引数リスト arg_ptr の先頭をセットします
ヘッダ - stdarg.h
arg_ptr - 引数リストへのポインタを指定します
prev_param - 最初のオプション引数の直前の引数

void va_end( va_list arg_ptr );
引数リストへのアクセスを終了し、ポインタをNULLにします
ヘッダ - stdarg.h
arg_ptr - 引数リストへのポインタを指定します

[Quote]:http://wisdom.sakura.ne.jp/programming/c/c62.html

| BLOG TOP |

copyright © Manhattan life all rights reserved.Powered by FC2ブログ