第35章 配列再考

 配列変数を引数に取りたい。そんなときはどうすればよいのでしょうか? 今回はそんなことをやってみます。


 では、今回の要点です。


 では、いってみましょう。


 配列を引数にとるにはどうすればよいのでしょうか。

 実はこれは一回やっています。第24章(文字列をいじろう)でです。配列(文字列)を引数にとるときは、配列変数の名前を渡すと言いました。

 問題なのは関数の定義の方です。こちらの方はまだ触れていません。

 文字列に使っていた配列は大きさがまちまちでした。よって、大きさを指定する必要はないと思われます。そう考えると、

void func(int array[]);
    .
    .
    .
int array[5];
func(array);

のようになるはずなのですが...。

 では、試してみましょう。

プログラム実行結果
// Array2.cpp
#include <iostream.h>

void Display(int array[])
{
    int i;
    for(i = 0; i < 5; i++)
        cout << array[i] << endl;
}

int main()
{
    int i;
    int n[5];

    for(i = 0; i < 5; i++)
        n[i] = i * 5;
    Display(n);

    return 0;
}
0
5
10
15
20

 どうやらこれでいいみたいですね。

 では、まとめてみましょう。

 配列変数を引数にとる場合は、関数の定義の方は

void func(int array[]);

のように、大きさの未定な配列変数の形にし、使用する方は

func(n);

のように、配列変数の名前を渡すようにすればよいのです。


 さて、前に「引数用の変数が作られて、引数はそこに入れられる」と話しました。しかし、配列変数も本当にそうなっているのでしょうか?

 仮に

float a[1000];

という配列があったとします。float の大きさは4バイトです。なので、これは4000バイトになります。

 4000バイトものデータをコピーするのははっきり言って無駄です。それよりは配列の位置を渡して大元の配列を利用するほうがはるかに実用的でしょう。そして、実際にそうなっています。

 実は、上のプログラムの引数 array は配列変数の形をしていますがポインタなのです。そして、配列変数の名前は配列変数の先頭のアドレスを示すのです。

 こうして、ポインタお得意の参照、つまりアドレスを介して変数を操作する機能を使って配列変数を操作しているのです。


 では、さらに詳しく説明しましょう。

 配列変数は、メモリ上に連続して存在しています。例えば、上の float a[1000]; では、

変数 a[0] a[1] a[2] ... a[999]
アドレス
(例)
6618592

6618595
6618596

6618599
6618600

6618603
... 6622588

6622591

のようになっています。

 先頭は a[0] です。そして、それを基準に a[1] はその4バイト先に、a[2] はそのさらに4バイト先、つまり a[0] から8バイト先にあります。4バイトずつなのは、float の大きさが4バイトだからです。

 つまり、先頭のアドレスと変数の型さえわかっていれば a[1] や a[2] 、果ては a[999] のアドレスまでわかってしまうのです。ですから、型を指定し、先頭のアドレスを渡すだけで配列変数を参照することができるのです。

 そして、配列変数の先頭のアドレスは、いちいち &a[0] のようにしなくても、a 、つまり配列変数名だけで取得できるようになっています。

 では、そのアドレスをどう扱えばいいのでしょうか?

 それは、配列変数と同じように [ ] を使えばいいのです。(* を使う方法もありますが、今はまだ話しません。)

 実は、この [ ] という演算子([ ] も「演算子」になります)は、<アドレス>[<番号>] としたときに、指定した <アドレス> から <番号> × <型の大きさ> だけ進めたところにある変数を使用するときに使うものなのでした。

 このことによりポインタを配列変数であるかのように扱うことができるのです。

 以上が配列変数を引数にとる際のメカニズムです。

 また、もちろん

void func(int array[]);

void func(int* array);

と書いても構いません。この2つは全く同じです。


 次回は、今回話したことを実際に確かめてみようと思います。

 では、今回の要点です。


 では、次回まで。


第34章 ポインタ天国3 | 第36章 配列再々考

Last update was done on 1999.4.15

この講座の著作権はロベールが保有しています