第6講 ポインタの学習
第1話 ポインタとは?
VC+とVB違いの1つは、このポインタの有無です。
VBにはポインタがありませんが、VC++にはポインタがあります。
このポインタの存在がC言語を魅力的なものにしていると同時に難しくしています。
ポインタは前講で学んだ配列に似たものですが、
配列より遙かに応用範囲・適応範囲が広いのです。
ポインタは次のように宣言されます。
int* a;
または
int *a;
理由は後で説明しますが、
ポインタを宣言した後、次のように初期化しないとエラーします。
a=(int *)malloc;
mallocはメモリの割り当てですが、これを使うためには冒頭でインクルードファイルstdlib.hを読み込んでおく必要があります。
宣言して初期化しておくとあたかも配列のように使うことができます。
ただし、a[3]に相当するものは、*(a+3)です。
では、新しいプロジェクトから次のようなForm1を作り、
実行をダブルクリックして、次のようにコーティングしてみましょう。
#pragma once
#include<stdlib.h>
namespace ポインタの学習 {
・
・
・
#pragma endregion
private: System::Void button1_Click(System::Object^ sender, System::EventArgs^
e) {
//ポインタの宣言
int* a;
//変数の宣言
int i;
//ポインタの初期化(メモリ割り当て)
a=(int *)malloc;
//ポインタに内容を代入
for(i=0;i<5;i++)*(a+i)=2*i+1;
//文字変数の宣言
String^ w=L"";
//ポインタの内容の表示
for(i=0;i<5;i++)w+=(*(a+i)).ToString()+L" ";
label1->Text=w;
}
};
}
実行結果
さて、コーティングを次のように変更して、ポインタが配列と似ていることを確認しましょう。
#pragma endregion
private: System::Void button1_Click(System::Object^ sender, System::EventArgs^
e) {
//配列の宣言
int a[5];
//変数の宣言
int i;
//配列に内容を代入
for(i=0;i<5;i++)a[i]=2*i+1;
//文字変数の宣言
String^ w=L"";
//配列の内容の表示
for(i=0;i<5;i++)w+=(a[i]).ToString()+L" ";
label1->Text=w;
}
};
}
実行結果
つまり、配列のa[i]とポインタの*(a+i)が全く同じ働きをしていることがわかります。
この限りでは、ポインタは1次元配列です。
もちろん、前講で学習したとおり多次元配列は1次元配列で表現できたので、
多次元配列をポインタで表現することもできます。
3次元配列を1次元配列で対応させる場合
a[4][3][5]とb[60]なら
a[i][j][k]=b[15*i+5*j+k]
3次元配列をポインタで対応させる場合
int* c;
c=(int *)malloc;
a[i][j][k]=*c(15*i+5*j+k)
[i][j][k]と15*i+5*j+kでは、[i][j][k]の方が記述が簡単です。
しかも、配列の場合はいちいち計算しなくてもよいのに対して、
ポインタでは計算しなければなりません。
15*i+5*j+kの15は、a[4][3][5]の3と5を使い3×5から15です。
また、15*i+5*j+kの5は、a[4][3][5]の5です。
このようにポインタでは、各次元の添え字数を勘案して計算しなければなりません。
今の時点では、配列とポインタを比較した場合、配列に軍配があがりそうですが、
ポインタがC言語を魅力的なものにしているとはどういうことでしょうか。
第5講第10話へ 第2話へ