C言語の入門をさらに深めるために、ポインタ、配列、関数という重要な要素について解説します。これらはC言語の力を最大限に引き出すために必須の知識です。
1. 配列 (Arrays) 📦
配列は、同じデータ型の変数を複数、メモリ上に連続して並べて管理するための仕組みです。
宣言と初期化
配列を宣言するには、データ型、配列名、そして要素の数を角括弧 []
で指定します。
// int型の要素を5つ持つ配列を宣言
int numbers[5];
// 宣言と同時に初期化
int scores[3] = {80, 75, 90};
// 要素数を省略して初期化 (要素数は3と自動で決定される)
char vowels[] = {'a', 'e', 'i', 'o', 'u'};
要素へのアクセス
配列の要素には、**インデックス(添字)**を使ってアクセスします。C言語のインデックスは必ず 0から 始まります。
int scores[3] = {80, 75, 90};
// 最初の要素 (80) にアクセス
printf("1番目の点数: %d\n", scores[0]); // 出力: 80
// 2番目の要素の値を変更 (75を85に)
scores[1] = 85;
// 最後の要素 (90) にアクセス
printf("3番目の点数: %d\n", scores[2]); // 出力: 90
2. 関数 (Functions) ⚙️
関数は、特定の処理をひとまとまりにしたもので、プログラムの再利用性や可読性を高めます。
関数の定義と呼び出し
関数は、戻り値の型、関数名、引数(ひきすう)リスト、そして処理本体で構成されます。
C
// ① 関数の定義 (2つの整数を受け取り、その合計を返す関数)
int add(int a, int b) {
int sum = a + b;
return sum; // 処理結果を呼び出し元に返す
}
int main(void) {
// ② 関数の呼び出し
int result = add(5, 3); // 5と3を渡し、8を受け取る
printf("合計: %d\n", result); // 出力: 8
return 0;
}
プロトタイプ宣言
main
関数より後に関数を定義する場合や、複数のファイルで関数を使う場合は、関数のヘッダー部分だけを先に記述するプロトタイプ宣言が必要です。
C
// プロトタイプ宣言 (main関数より前に記述)
int add(int a, int b);
int main(void) {
int result = add(5, 3);
return 0;
}
// 関数の定義
int add(int a, int b) {
return a + b;
}
3. ポインタ (Pointers) 🧭
ポインタは、**メモリのアドレス(番地)**を格納するための変数です。C言語の最も強力で、最も難しいとされる機能です。
ポインタの宣言
ポインタ変数を宣言するには、データ型の後にアスタリスク *
を付けます。
int num = 100;
// numの型 (int) のアドレスを格納するポインタを宣言
int *ptr;
重要な2つの演算子
ポインタを理解するために、以下の2つの演算子を把握する必要があります。
- アドレス演算子 (
&
): 変数の**アドレス(番地)**を取得します。 - 間接参照演算子 (
*
): ポインタが指すアドレスに格納されている値を取得します。
ポインタの利用
int num = 100;
int *ptr;
// 1. 変数numのアドレスをポインタptrに代入
ptr = #
printf("numの値: %d\n", num); // 出力: 100
// 2. ptrが指すアドレスに格納されている値 (numの値) を取得
printf("ptr経由の値: %d\n", *ptr); // 出力: 100
// 3. *ptr経由で値を変更 (numの値が200に変わる)
*ptr = 200;
printf("変更後のnumの値: %d\n", num); // 出力: 200
ポインタと配列
C言語では、配列名はしばしば配列の最初の要素を指すポインタとして扱われます。
int arr[3] = {10, 20, 30};
// arrは最初の要素 (&arr[0]) のアドレスを示すポインタとして機能する
printf("arr[1]の値: %d\n", arr[1]);
// ポインタ演算: arrのアドレスから1つ進んだ場所 (*(arr + 1)) の値
printf("ポインタ演算: %d\n", *(arr + 1)); // 出力: 20
ポインタは、動的なメモリ管理や、引数として大きなデータを効率よく関数に渡す際などに非常に重要になります。