put
系関数,printf
系関数 ライブラリ stdio.h
で出力用に用意された関数は数多くあります。次はその一部です。
関数(プロトタイプ:2段目) | 出力されるもの | 出力先 |
fputc(文字定数, ストリーム) | 文字定数 ( c はASCIIコード) | ストリーム |
putc(文字定数, ストリーム) | 文字定数 | ストリーム |
putchar(文字定数) | 文字定数 | 標準出力 |
fputs(文字列リテラル, ストリーム) | 文字列リテラル | ストリーム |
puts(文字列リテラル) | 文字列リテラル | 標準出力 |
fprintf(ストリーム, フォーマット, 出力元) | フォーマット | ストリーム |
printf(フォーマット, 出力元) | フォーマット | 標準出力 |
snprintf(char型配列, 文字数, フォーマット, 出力元) | フォーマット 但し, 文字数 - 1 文字まで。 | char 型配列 |
sprintf(char型配列, フォーマット, 出力元) | フォーマット | char 型配列 |
* プロトタイプ内の const
や restrict
は後に学びます。また,FILE
はライブラリ stdio.h
で typedef
によって型定義された「型」です。
ストリーム
とは出力先です。ライブラリ stdio.h
には次の三つが用意されています。[C99, 7.19.1, 3]
stdout | 標準出力 |
stderr | 標準エラー出力 |
stdin | 標準入力 |
例えば,printf
は,fprintf
のストリーム に stdout
を指定したのと同じです。同じことは,putc
と putchar
についても言えます。[C99, 7.19.6.3, 7.19.7.9]
|
|
大きくは put
系と printf
系に分けられ,前者は指定された文字,あるいは文字列を出力しますが,後者はフォーマットを出力します。「フォーマット」とは,変換指定子を含む文字列のことです。変換指定子は出力元の変数の出力スタイルを指定します。
■変換指定子(conversion specifier)[C99, 7.19.6.1]
char, short, int, long, long long
%d ,%i | int を符号付き(signed)の10進数へ変換。 |
%u ,%o ,%x ,%X | 各々 unsigned int を符号無し(unsigned)の10進数,8進数,16進数 (0-9abcdef形式),16進数 (0-9ABCDEF形式) へ変換。 |
* long には l を,long long には ll を,size_t には z を,ptrdiff_t には t を付す。[例] long を符号付き10進数に変換する場合:%ld char や short は整数拡張(integer promotions)が施されるので int のケースとなる。元の型に変換し直すには,char には hh を,short には h を付す。付言すると, signed の非負値は同一の型の unsigned の範囲であり,それらは同じ値で表現される。これは関数の引数や戻り値 (return value,返却値) での互換性を意味する。[C99, 6.2.5, 9 & fn.31] | |
%c | ASCII文字。unsigned char に変換された後の文字。 |
%s | char 型配列用。変数に示したアドレスの文字からナル文字 (null character, '\0' ) までを出力。(但し,ナル文字は出力されない。) |
float, double, long double
%f ,%F | 小数点表示 |
%e ,%E | 指数表示 |
* long double 型の出力の場合,L を付す。[C99, 7.19.6.1, 7][例] %Lf 付言すると,仕様書(C99)には float に対する出力の記載がない。これは「規定の実引数拡張」(default argument promotions)が適用されるため。 |
型 *
%p | 出力形式は処理系依存。 |
/* Example 13.1 */ #include <stdio.h> int main(void) { char str[] = "ABCDEF"; char *p; for(p = str; *p; p++) printf("%td\t%s\t%c\t(%u, %o, %x)\t[%p]\n", p - str, p, *p, *p, *p, *p, p); return 0; }
実行結果です。(丸括弧内は ASCIIコード番号,角括弧内はアドレスです。)
0 ABCDEF A (65, 101, 41) [0xbffffa98] 1 BCDEF B (66, 102, 42) [0xbffffa99] 2 CDEF C (67, 103, 43) [0xbffffa9a] 3 DEF D (68, 104, 44) [0xbffffa9b] 4 EF E (69, 105, 45) [0xbffffa9c] 5 F F (70, 106, 46) [0xbffffa9d]
/* Example 13.2 */ #include <stdio.h> int main(void) { fprintf(stdout, "This is a test.\n"); fprintf(stderr, "Error!\n"); return 0; }
標準エラー出力されているか否かを実験してみます。(太字部分が入力した箇所です。)
% ./a.out This is a test. Error! % ./a.out > tmp.txt Error! % cat tmp.txt This is a test. %
2回目の実行でファイル tmp.txt
へ出力をリダイレクトすると,エラーメッセージのみが出力されています。そして,tmp.txt
には標準出力部分のみが書き込まれています。