名前空間
変種
操作

vprintf, vfprintf, vsprintf, vsnprintf, vprintf_s, vfprintf_s, vsprintf_s, vsnprintf_s

提供: cppreference.com
< c‎ | io
 
 
ファイル入出力
関数
ファイルアクセス
直接入出力
書式なし入出力
(C11以前)(C11およびそれ以降)
(C95)(C95)
(C95)
(C95)(C95)
(C95)
(C95)
書式付き入力
書式付き出力
vprintfvfprintfvsprintfvsnprintfvprintf_svfprintf_svsprintf_svsnprintf_s
(C99)(C11)(C11)(C11)(C11)
ファイル位置操作
エラー処理
ファイルに対する操作
 
ヘッダ <stdio.h> で定義
(1)
int vprintf( const char *format, va_list vlist );
(C99以前)
int vprintf( const char *restrict format, va_list vlist );
(C99およびそれ以降)
(2)
int vfprintf( FILE *stream, const char *format, va_list vlist );
(C99以前)
int vfprintf( FILE *restrict stream, const char *restrict format,
              va_list vlist );
(C99およびそれ以降)
(3)
int vsprintf( char *buffer, const char *format, va_list vlist );
(C99以前)
int vsprintf( char *restrict buffer, const char *restrict format,
              va_list vlist );
(C99およびそれ以降)
int vsnprintf( char *restrict buffer, int bufsz,
               const char *restrict format, va_list vlist );
(4) (C99およびそれ以降)
int vprintf_s( const char *restrict format, va_list arg);
(5) (C11およびそれ以降)
int vfprintf_s( FILE *restrict stream, const char *restrict format,
                va_list arg);
(6) (C11およびそれ以降)
int vsprintf_s( char *restrict buffer, rsize_t bufsz,
                const char *restrict format, va_list arg);
(7) (C11およびそれ以降)
int vsnprintf_s(char *restrict buffer, rsize_t bufsz,
                const char *restrict format, va_list arg);
(8) (C11およびそれ以降)

vlist によって定義される位置からデータをロードし、それらを文字列に変換し、結果を様々なシンクに書き込みます。

1) 結果を stdout に書き込みます。
2) 結果をファイルストリーム stream に書き込みます。
3) 結果を文字列 buffer に書き込みます。
4) 結果を文字列 buffer に書き込みます。 最大 buf_size - 1 文字が書き込まれます。 buf_size がゼロでなければ、結果の文字列はヌル文字で終端されます。 buf_size がゼロの場合は、何も書き込まれず、 buffer はヌルポインタであっても構いませんが、その場合でも戻り値 (本来書き込まれたはずのヌル終端を含まないバイト数) は計算され、返されます。
5-8) (1-4) と同じですが、以下のエラーが実行時に検出され、現在設定されている制約ハンドラ関数を呼びます。
  • format に変換指定子 %n が存在する。
  • %s に対応するいずれかの引数がヌルポインタ。
  • format または buffer がヌルポインタ。
  • bufsz がゼロまたは RSIZE_MAX より大きい。
  • 文字列または文字変換指定子のいずれかでエンコーディングエラーが発生した。
  • (vsprintf_s の場合のみ) buffer に格納される文字列 (末尾のヌルを含む) が bufsz を超える
すべての境界チェック付き関数と同様に、 vprintf_svfprintf_svsprintf_s および vsnprintf_s__STDC_LIB_EXT1__ が処理系によって定義されていて、 <stdio.h> をインクルードする前にユーザが __STDC_WANT_LIB_EXT1__ を整数定数 1 に定義した場合にのみ、利用可能であることが保証されます。

目次

[編集] 引数

stream - 書き込む出力ストリーム
buffer - 書き込む文字列を指すポインタ
bufsz - 最大 bufsz - 1 文字およびヌル終端が書き込まれる可能性があります
format - データの解釈方法を指定するヌル終端文字列を指すポインタ。

書式文字列は、変更されずに出力ストリームにコピーされる (% を除く) 通常のマルチバイト文字と、変換仕様から構成されます。 各変換仕様は以下の書式を持ちます。

  • 最初の % 文字。
  • (オプション) 変換の動作を変更する1つ以上のフラグ。
  • - : 変換の結果をフィールド内で左詰めします。 (デフォルトでは右詰めされます)。
  • + : 符号付き変換の符号が必ず変換の結果の前に付加されます (デフォルトでは負の場合にのみマイナスが結果の前に付加されます)。
  • 空白 : 符号付き変換の結果が符号文字で始まらない、または空の場合、空白が結果の前に付加されます。 + フラグが存在する場合、このフラグは無視されます。
  • # : 変換の代替形式が行われます。 正確な効果は下の表を参照してください。 記載がなければ動作は未定義です。
  • 0 : 整数または浮動小数点数の変換に対して、フィールドをパディングするために空白文字の代わりに先行するゼロが使用されます。 整数の場合、精度が明示的に指定されていれば、このフラグは無視されます。 それ以外の変換に対してこのフラグを使用した結果は未定義動作です。 - フラグが存在する場合、このフラグは無視されます。
  • (オプション) 最小フィールド幅を指定する整数値または *。 結果は、必要の場合は、左詰めの場合は右側に、右詰めの場合は左側に、 (デフォルトでは) 空白文字で、パディングされます。 * が使用された場合、幅は int 型の追加の引数によって指定されます。 引数の値が負の場合は、 - フラグと正のフィールド幅として解釈されます。 (ノート: これは最小の幅です。 値が切り捨てられることはありません。)
  • (オプション) 変換の精度を指定する . に続く整数または *、またはそのいずれも続かない単体の .* が使用された場合、 精度int 型の追加の引数によって指定されます。 この引数の値が負の場合、それは無視されます。 数値も * も続かない単体の . が使用された場合、精度はゼロとして扱われます。 精度 の正確な効果は下の表を参照してください。
  • (オプション) 引数のサイズを指定する長さ修飾子
  • 変換書式指定子。

以下の書式指定子が利用できます。

変換指定子 説明 引数の型
長さ修飾子 hh

(C99)

h なし l ll

(C99)

j

(C99)

z

(C99)

t

(C99)

L
% % を書き込みます。 変換仕様全体が %% でなければなりません。 N/A N/A N/A N/A N/A N/A N/A N/A N/A
c

単一の文字を書き込みます。

引数はまず unsigned char に変換されます。 l 修飾子が指定された場合は、引数はまず、 wchar_t[2] 引数で %ls によって行われたかのように、文字列に変換されます。

N/A N/A
int
wint_t
N/A N/A N/A N/A N/A
s

文字列を書き込みます。

引数は文字配列の最初の要素を指すポインタでなければなりません。 精度は書き込まれる最大バイト数を指定します。 精度が指定されていない場合は、最初のヌル終端に達するまで、すべてのバイトが書き込まれます (ヌル終端は書き込まれません)。 l 指定子が使用された場合は、引数は wchar_t 配列の最初の要素を指すポインタでなければなりません。 それは、ゼロ初期化された変換状態を使用して wcrtomb を呼んだかのように、文字配列に変換されます。

N/A N/A
char*
wchar_t*
N/A N/A N/A N/A N/A
d
i

符号付き整数を10進表現 [-]dddd に変換します。

精度は出力される最小桁数を指定します。 デフォルトの精度は 1 です。 変換後の値と精度がどちらも 0 であれば変換結果は空文字列になります。

signed char
short
int
long
long long
signed size_t
N/A
o

符号なし整数を8進数表現 oooo に変換します。

精度は出力される最小桁数を指定します。 デフォルトの精度は 1 です。 変換後の値と精度がどちらも 0 であれば変換結果は空文字列になります。 代替表現では前にゼロを1個付加するために必要に応じて精度が増えます。 その場合、変換後の値と精度がどちらも 0 であれば単一の 0 が書き込まれます。

unsigned char
unsigned short
unsigned int
unsigned long
unsigned long long
unsigned version of ptrdiff_t
N/A
x
X

符号なし整数を16進数表現 hhhh に変換します。

x 変換の場合は文字 abcdef が使用されます。 X 変換の場合は文字 ABCDEF が使用されます。

精度は出力される最小桁数を指定します。 デフォルトの精度は 1 です。 変換後の値と精度がどちらも 0 であれば変換結果は空文字列になります。 代替表現では変換結果がゼロでなければ結果の前に 0x または 0X が付加されます。

N/A
u

符号なし整数を10進数表現 dddd に変換します。

精度は出力される最小桁数を指定します。 デフォルトの精度は 1 です。 変換後の値と精度がどちらも 0 であれば変換結果は空文字列になります。

N/A
f
F

浮動小数点数[-]ddd.ddd 形式の10進数表記に変換します。

精度は小数点以下の最小桁数を指定します。 デフォルトの精度は 6 です。 代替表現では小数点の後に何もなくても小数点文字が書き込まれます。 無限大および非数の変換形式についてはノートを参照してください。

N/A N/A
double
double (C99)
N/A N/A N/A N/A
long double
e
E

浮動小数点数を10進数の指数表記に変換します。

e 変換の場合は [-]d.ddde±dd 形式が使用されます。 E 変換の場合は [-]d.dddE±dd 形式が使用されます。

指数は少なくとも2桁あり、必要に応じて桁数が増えます。 値が 0 であれば、指数も 0 になります。 精度は小数点以下の最小桁数を指定します。 デフォルトの精度は 6 です。 代替表現では小数点の後に何もなくても小数点文字が書き込まれます。 無限大および非数の変換形式についてはノートを参照してください。

N/A N/A N/A N/A N/A N/A
a
A

(C99)

浮動小数点数を16進数の指数表記に変換します。

a 変換の場合は [-]0xh.hhhp±d 形式が使用されます。 A 変換の場合は [-]0Xh.hhhP±d 形式が使用されます。

引数が正規化浮動小数点数でなければ、最初の16進数桁は 0 になります。 値が 0 であれば、指数も 0 になります。 精度は小数点以下の最小桁数を指定します。 デフォルトの精度は値を正確に表現するのに十分な値です。 代替表現では小数点の後に何もなくても小数点文字が書き込まれます。 無限大および非数の変換形式についてはノートを参照してください。

N/A N/A N/A N/A N/A N/A
g
G

浮動小数点数を値と精度に応じて10進数表記または10進数の指数表記に変換します。

g 変換の場合は e または f 形式の変換が行われます。 G 変換の場合は E または F 形式の変換が行われます。

P を非ゼロの場合は精度と等しい値、精度が指定されていない場合は 6、精度が 0 の場合は 1 と置いたとき、 E 形式の変換で指数が X である場合、

  • P > X ≥ −4 であれば、変換は f または F の形式と P − 1 − X の精度を持ちます。
  • そうでなければ、変換は e または E の形式と P − 1 の精度を持ちます。

代替表現が要求されなければ、末尾のゼロは削除され、小数点以下が残っていなければ、小数点文字も削除されます。 無限大および非数の変換形式についてはノートを参照してください。

N/A N/A N/A N/A N/A N/A
n

関数のこの呼び出しによってそれまでに書き込まれた文字数を返します。

結果は引数の指している値に書き込まれます。 仕様はフラグフィールド幅精度のいずれも含んでいてはいけません。

signed char*
short*
int*
long*
long long*
signed size_t*
N/A
p

ポインタを定義する処理系定義の文字シーケンスを書き込みます。

N/A N/A void* N/A N/A N/A N/A N/A N/A

浮動小数点変換関数は無限大を inf または infinity に変換します。 いずれが使用されるかは処理系定義です。

非数は nan または nan(char_sequence) に変換されます。 いずれが使用されるかは処理系定義です。

変換 F, E, G, A は代わりに INF, INFINITY, NAN を出力します。

%cint 引数を期待しますが、可変長引数関数が呼ばれるときに行われる整数拡張のため、 char を渡しても安全です。

固定幅の整数型 (int8_t など) に対する正しい変換仕様はヘッダ <inttypes.h> で定義されています (PRIdMAX, PRIuMAX などは %jd, %ju などの同義語ですが)。

メモリに書き込む変換指定子 %n は、書式文字列がユーザ入力に依存する場合、セキュリティエクスプロイトのよくあるターゲットであり、境界チェック付きの printf_s ファミリーの関数ではサポートされていません。

変換指定子それぞれの動作後に副作用完了点があります。 これにより同じ変数に複数の %n の結果を格納することができ、またエッジケースとして、同じ呼び出しの中で先行する %n によって変更された値を表示することができます。

変換仕様が無効な場合、動作は未定義です。


vlist - 表示するデータを格納している可変長引数リスト

[編集] 戻り値

1-3) 成功した場合は書き込まれた文字数、エラーが発生した場合は負の値。
4) 成功した場合は書き込まれた文字数、エラーが発生した場合は負の値。 結果の文字列が buf_size 制限のために切り捨てられた場合は、もし制限が課されなければ書き込まれたであろう合計文字数 (終端のヌルバイトは含みません) を返します。
5,6) 出力ストリームに転送された文字数。 出力エラー、実行時制約違反エラー、またはエンコーディングエラーが発生した場合は負の値。
7) buffer に書き込まれた文字数 (ヌル文字はカウントされません。 buffer がヌルポインタでなく、 bufsz がゼロでなく RSIZE_MAX よりも大きくなければ、ヌル文字は常に書き込まれます)。 実行時制約違反の場合はゼロ。 エンコーディングエラーの場合は負の値。
8) もし bufsz を無視したならば buffer に書き込まれたであろう文字数 (終端のヌル文字は含みません。 buffer がヌルポインタでなく、 bufsz がゼロでなく RSIZE_MAX よりも大きくなければ、ヌル文字は常に書き込まれます)。 実行時制約違反またはエンコーディングエラーが発生した場合は負の値。

[編集] ノート

これらのすべての関数は va_arg を少なくとも1回は呼び、戻った後 arg の値は不定になります。 これらの関数は va_end を呼ばす、それは呼び出し元が行わなければなりません。

vsnprintf_s は、 vsprintf_s と異なり、結果を buffer の指す配列内に収まるように切り捨てます。

[編集]

#include <stdio.h>
#include <stdarg.h>
#include <time.h>
 
void debug_log(const char *fmt, ...)
{
    struct timespec ts;
    timespec_get(&ts, TIME_UTC);
    char time_buf[100];
    size_t rc = strftime(time_buf, sizeof time_buf, "%D %T", gmtime(&ts.tv_sec));
    snprintf(time_buf + rc, sizeof time_buf - rc, ".%06ld UTC", ts.tv_nsec / 1000);
 
    va_list args1;
    va_start(args1, fmt);
    va_list args2;
    va_copy(args2, args1);
    char buf[1+vsnprintf(NULL, 0, fmt, args1)];
    va_end(args1);
    vsnprintf(buf, sizeof buf, fmt, args2);
    va_end(args2);
 
    printf("%s [debug]: %s\n", time_buf, buf);
}
 
int main(void)
{
    debug_log("Logging, %d, %d, %d", 1, 2, 3);
}

出力例:

02/20/15 21:58:09.072683 UTC [debug]: Logging, 1, 2, 3

[編集] 参考文献

  • C11 standard (ISO/IEC 9899:2011):
  • 7.21.6.8 The vfprintf function (p: 326-327)
  • 7.21.6.10 The vprintf function (p: 328)
  • 7.21.6.12 The vsnprintf function (p: 329)
  • 7.21.6.13 The vsprintf function (p: 329)
  • K.3.5.3.8 The vfprintf_s function (p: 597)
  • K.3.5.3.10 The vprintf_s function (p: 598-599)
  • K.3.5.3.12 The vsnprintf_s function (p: 600)
  • K.3.5.3.13 The vsprintf_s function (p: 601)
  • C99 standard (ISO/IEC 9899:1999):
  • 7.19.6.8 The vfprintf function (p: 292)
  • 7.19.6.10 The vprintf function (p: 293)
  • 7.19.6.12 The vsnprintf function (p: 294)
  • 7.19.6.13 The vsprintf function (p: 295)
  • C89/C90 standard (ISO/IEC 9899:1990):
  • 4.9.6.7 The vfprintf function
  • 4.9.6.8 The vprintf function
  • 4.9.6.9 The vsprintf function

[編集] 関連項目

stdout、ファイルストリームまたはバッファに可変個引数リストを使用して書式付きワイド文字出力を書き出します
(関数) [edit]
stdout、ファイルストリームまたはバッファに書式付き出力を書き出します
(関数) [edit]
stdin、ファイルストリームまたはバッファから可変個引数リストを使用して書式付き入力を読み取ります
(関数) [edit]
vprintf, vfprintf, vsprintf, vsnprintfC++リファレンス