配列名、または配列型の任意の式は、次のいずれかでない限り、配列の最初の要素へのポインターに暗黙的に変換されます。
- 単項
&
(address-of)式のオペランド(最初の要素ではなく、配列全体のアドレスを生成します-同じメモリアドレス、異なるタイプ)。また
- 演算子のオペランド
sizeof
(sizeof arr
ポインターのサイズではなく、配列のサイズを生成します)。また
- 演算子のオペランド
_Alignof
(_Alignof arr
ポインターのアラインメントではなく、配列のアラインメントを生成します); また
- arraryオブジェクトを初期化するために使用される初期化子の文字列リテラル。
_Alignof
C2011の新機能です。
(変換はしばしば「減衰」と呼ばれます。)
これらはいずれもここには当てはまらないため、ポインタオブジェクトをインクリメントarr++
しようとします。問題は、ポインタオブジェクトがなく、ポインタ値だけであるということです。arr
、ポインタ値に減衰した後は、左辺値ではありません。つまり、代入の左側に表示したり、のオペランドとして表示したりすることはできません++
。
同様に、与えられた:
int x;
式x
は左辺値であるため、次のように記述できますx = 42;
が、式(x + 1)
は左辺値ではないため、を書き込むことはできません(x + 1) = 42;
。オブジェクトx
を参照しているため、に割り当てることができます。 オブジェクトを参照しないため、割り当てるものはありません。 、減衰した後は、オブジェクトも参照しません(配列オブジェクトはありますが、ポインタオブジェクトはありません)。(x+1)
arr
(あなたの使用はarr != arr + 4
手がかりになるはずでした;それは決して真実ではありえません。)
これではなく:
char arr[] = {'a', 'b', 'c', 'd'};
for (; arr != arr + 4; arr++) {
printf("%c", *arr);
}
あなたはこれを書くことができます:
char arr[] = {'a', 'b', 'c', 'd'};
char *ptr;
for (ptr = arr; ptr != arr + 4; ptr++) {
printf("%c", &ptr);
}
ちなみに、プログラムの上部で、これを変更する必要があります。
main()
これに:
#include <stdio.h>
int main(void)
また、 comp.lang.c FAQまで実行し、歩かないでください。セクション6「配列とポインタ」をお読みください。