C Language
データ型
サーチ…
備考
-
char
は1バイトである必要がありますが、ほとんどの現代のコンピュータプラットフォームでは8ビットと定義されていますが、1バイトは8ビット(通常はオクテットとも呼ばれます)である必要はありません 。実装のchar
あたりのビット数は、<limits.h>
で定義されているCHAR_BIT
マクロによって提供されます。 POSIXでは、1バイトが8ビットである必要があります。 - 固定幅の整数型はまばらに使用する必要があります。Cの組み込み型はすべてのアーキテクチャで自然に設計されています。固定幅の型は、(ネットワーキングなどの)具体的なサイズの整数が明示的に必要な場合にのみ使用してください。
整数型と定数
署名された整数は、これらの型のものである可能性があります( short
後のint
またはlong
はオプションです)。
signed char c = 127; /* required to be 1 byte, see remarks for further information. */
signed short int si = 32767; /* required to be at least 16 bits. */
signed int i = 32767; /* required to be at least 16 bits */
signed long int li = 2147483647; /* required to be at least 32 bits. */
signed long long int li = 2147483647; /* required to be at least 64 bits */
これらの符号付き整数型のそれぞれは、符号なしバージョンを持ちます。
unsigned int i = 65535;
unsigned short = 2767;
unsigned char = 255;
しかし、すべてのタイプのchar
signed
た場合のバージョンが想定されるsigned
またはunsigned
一部が省略されています。 char
型はsigned char
とunsigned char
とは異なる第3の文字型を構成し、符合はプラットフォームによって異なります。
さまざまなタイプの整数定数(Cジャーゴンのリテラルと呼ばれます )は、それぞれの接頭辞または接尾辞に基づいて、異なるベースと異なる幅で書き込むことができます。
/* the following variables are initialized to the same value: */
int d = 42; /* decimal constant (base10) */
int o = 052; /* octal constant (base8) */
int x = 0xaf; /* hexadecimal constants (base16) */
int X = 0XAf; /* (letters 'a' through 'f' (case insensitive) represent 10 through 15) */
小数定数は常にsigned
ます。 16進定数は0x
または0X
で始まり、8進定数は0
始まり0
。後者の2つは、値がunsigned
付きの型に収まるかどうかによってunsigned
signed
またはunsigned
です。
/* suffixes to describe width and signedness : */
long int i = 0x32; /* no suffix represent int, or long int */
unsigned int ui = 65535u; /* u or U represent unsigned int, or long int */
long int li = 65536l; /* l or L represent long int */
接尾辞がなければ、定数はその値に適合する最初の型を持ちます。つまり、 INT_MAX
は可能な場合はlong
型、それ以外の場合はlong long
型より大きい10進定数です。
ヘッダーファイル<limits.h>
は、以下のように整数の限界が記述されています。それらの実装定義値は、以下に示すものと同じかそれ以上の大きさ(絶対値)でなければならない。
マクロ | タイプ | 値 |
---|---|---|
CHAR_BIT | ビットフィールドではない最小のオブジェクト(バイト) | 8 |
SCHAR_MIN | signed char | -127 / - (2 7 -1) |
SCHAR_MAX | signed char | +127 / 2 7 - 1 |
UCHAR_MAX | unsigned char | 255/2 8-1 |
CHAR_MIN | char | 下記参照 |
CHAR_MAX | char | 下記参照 |
SHRT_MIN | short int | -32767 / - (2〜15 - 1) |
SHRT_MAX | short int | +32767 / 2 15から 1 |
USHRT_MAX | unsigned short int | 2分の65535 16から 1 |
INT_MIN | int | -32767 / - (2〜15 - 1) |
INT_MAX | int | +32767 / 2 15から 1 |
UINT_MAX | unsigned int | 2分の65535 16から 1 |
LONG_MIN | long int | -2147483647 / - (2 31 - 1) |
LONG_MAX | long int | +2147483647 / 2 31 - 1 |
ULONG_MAX | unsigned long int | 4294967295/2 32-1 |
マクロ | タイプ | 値 |
---|---|---|
LLONG_MIN | long long int | -9223372036854775807 / - (2〜63 - 1) |
LLONG_MAX | long long int | 9223372036854775807/2 63から 1 |
ULLONG_MAX | unsigned long long int | 2分の18446744073709551615 64から 1 |
もし対象の値型char
符号拡張式で使用される場合、の値CHAR_MIN
と同じでなければならないSCHAR_MIN
の値CHAR_MAX
と同じでなければならないSCHAR_MAX
。型のオブジェクトの値場合char
ない符号拡張式で使用される場合、の値CHAR_MIN
0でなければならないとの値CHAR_MAX
と同じでなければならないUCHAR_MAX
。
C99標準には、固定幅の整数の定義を含む新しいヘッダー<stdint.h>
追加されました。より詳細な説明については、固定幅整数の例を参照してください。
文字列リテラル
Cの文字列リテラルは、リテラルゼロで終わる文字列です。
char* str = "hello, world"; /* string literal */
/* string literals can be used to initialize arrays */
char a1[] = "abc"; /* a1 is char[4] holding {'a','b','c','\0'} */
char a2[4] = "abc"; /* same as a1 */
char a3[3] = "abc"; /* a1 is char[3] holding {'a','b','c'}, missing the '\0' */
文字列リテラルは変更できません (実際には.rodataなどの読み取り専用メモリに置くことができます)。値を変更しようとすると、未定義の動作が発生します。
char* s = "foobar";
s[0] = 'F'; /* undefined behaviour */
/* it's good practice to denote string literals as such, by using `const` */
char const* s1 = "foobar";
s1[0] = 'F'; /* compiler error! */
複数の文字列リテラルはコンパイル時に連結されます。つまり、これらのような構文を書くことができます。
/* only two narrow or two wide string literals may be concatenated */
char* s = "Hello, " "World";
/* since C99, more than two can be concatenated */
/* concatenation is implementation defined */
char* s1 = "Hello" ", " "World";
/* common usages are concatenations of format strings */
char* fmt = "%" PRId16; /* PRId16 macro since C99 */
文字定数と同じ文字列リテラルは、異なる文字セットをサポートします。
/* normal string literal, of type char[] */
char* s1 = "abc";
/* wide character string literal, of type wchar_t[] */
wchar_t* s2 = L"abc";
/* UTF-8 string literal, of type char[] */
char* s3 = u8"abc";
/* 16-bit wide string literal, of type char16_t[] */
char16_t* s4 = u"abc";
/* 32-bit wide string literal, of type char32_t[] */
char32_t* s5 = U"abc";
固定幅整数型(C99以降)
ヘッダ<stdint.h>
はいくつかの固定幅の整数型定義を提供します。これらの型はオプションであり、プラットフォームが対応する幅の整数型を持ち、対応する符号付き型が負の値の2の補数表現を持つ場合にのみ提供されます。
固定幅タイプのヒントについては、備考を参照してください。
/* commonly used types include */
uint32_t u32 = 32; /* exactly 32-bits wide */
uint8_t u8 = 255; /* exactly 8-bits wide */
int64_t i64 = -65 /* exactly 64 bit in two's complement representation */
浮動小数点定数
C言語は、3つの必須本当の浮動小数点型、持っているfloat
、 double
、およびlong double
。
float f = 0.314f; /* suffix f or F denotes type float */
double d = 0.314; /* no suffix denotes double */
long double ld = 0.314l; /* suffix l or L denotes long double */
/* the different parts of a floating point definition are optional */
double x = 1.; /* valid, fractional part is optional */
double y = .1; /* valid, whole-number part is optional */
/* they can also defined in scientific notation */
double sd = 1.2e3; /* decimal fraction 1.2 is scaled by 10^3, that is 1200.0 */
ヘッダ<float.h>
は、浮動小数点演算のさまざまな制限を定義します。
浮動小数点演算は実装定義です。しかし、最新のプラットフォーム(arm、x86、x86_64、MIPS)のほとんどはIEEE 754浮動小数点演算を使用します。
Cには、上記の3つのオプションの複素浮動小数点型もあります。
宣言の解釈
Cの独特な構文上の特異性は、宣言が宣言されたオブジェクトを通常の表現のように使用することを反映することです。
同じ優先順位と結合性を持つ以下の演算子のセットは、宣言子で再利用されます。
- ポインタを示す単項
*
「逆参照」演算子。 - 配列を表すbinary
[]
"array subscription"演算子。 - 関数を表す(1 + n)-ary
()
"関数呼び出し"演算子。 - リストされた演算子の優先順位と結合性をオーバーライドする
()
グループ化括弧。
上記の3つの演算子は、以下の優先順位と結合性を持っています。
オペレーター | 相対優先順位 | 関連性 |
---|---|---|
[] (配列サブスクリプション) | 1 | 左から右へ |
() (関数呼び出し) | 1 | 左から右へ |
* (間接参照) | 2 | 右から左へ |
宣言を解釈するときには、識別子から外側に向かって開始し、上記の表に従って正しい順序で隣接する演算子を適用する必要があります。演算子の各アプリケーションは、次の英語の単語で置き換えることができます。
式 | 解釈 |
---|---|
thing[X] | のサイズのX の配列... |
thing(t1, t2, t3) | t1 、 t2 、 t3 を返して戻る関数... |
*thing | へのポインタ... |
したがって、英語の解釈の始まりは常に識別子で始まり、宣言の左側にある型で終わります。
例
char *names[20];
[]
は*
よりも優先されるので、解釈は次のとおりですnames
は、 char
へのポインタのサイズ20の配列です。
char (*place)[10];
優先順位を上書きするために括弧を使用する場合には、 *
最初に適用されている: place
サイズ10の配列へのポインタであるchar
。
int fn(long, short);
ここで心配する優先順位はありませんfn
はlong
、 short
、 int
を返す関数です。
int *fn(void);
最初に()
が適用されますfn
はvoid
を取ってint
へのポインタを返す関数です。
int (*fp)(void);
()
の優先順位をオーバーライドする: fp
は、 void
を取ってint
を返す関数へのポインタです。
int arr[5][8];
多次元配列はルールの例外ではありません。 []
演算子は、表の結合性に従って左から右の順番で適用されますarr
は、 int
のサイズ8の配列のサイズ5の配列です。
int **ptr;
2つの逆参照演算子は等しい優先順位を持つため、結合性が有効になります。演算子は右から左の順番で適用されますptr
はint
へのポインタへのポインタです。
複数の宣言
カンマは、単一のステートメント内で複数の宣言を区切るために、セパレータ(*はカンマ演算子のようには動作しません)として使用できます。次のステートメントには、5つの宣言が含まれています。int fn(void), *ptr, (*fp)(int), arr[10][20], num;
上記の例で宣言されたオブジェクトは次のとおりです。
-
fn
:void
を取ってint
を返す関数。 -
ptr
:int
へのポインタ。 -
fp
:機能の撮影へのポインタint
と返すint
。 -
arr
:int
のサイズ20の配列のサイズ10の配列。 -
num
:int
。
別の解釈
宣言は使用を反映するので、宣言は、オブジェクトに対して適用可能な演算子と、その式の最終的な結果の型の観点から解釈することもできます。左側にあるタイプは、すべての演算子を適用した後に得られる最終結果です。
/*
* Subscripting "arr" and dereferencing it yields a "char" result.
* Particularly: *arr[5] is of type "char".
*/
char *arr[20];
/*
* Calling "fn" yields an "int" result.
* Particularly: fn('b') is of type "int".
*/
int fn(char);
/*
* Dereferencing "fp" and then calling it yields an "int" result.
* Particularly: (*fp)() is of type "int".
*/
int (*fp)(void);
/*
* Subscripting "strings" twice and dereferencing it yields a "char" result.
* Particularly: *strings[5][15] is of type "char"
*/
char *strings[10][20];