5.4 アドレス計算 K&R プログラミング言語C
2010年02月04日
5.4 アドレス計算
- 正常にアドレスを指し示すポインタは
0
にはならない。 0
は異常値を表し、stdio.h
で定義されているNULL
を使う。- ポインタは同じ配列の要素を指し示している場合には、
==
,!=
,<
,>
,<=
,>=
などの関係演算子を利用できる。 - ポインタと整数との間の加減算は、ポインタが指し示すオブジェクトの型のサイズに応じて適切にスケールされる。
p + n
は(p の先頭アドレス) + (sizeof p) * n
となる。
正しいポインタ演算
- 同じ型のポインタの代入
- ポインタと整数の加算・減算
- 同じ配列の要素を指し示すポインタの引き算と比較
- ゼロ(
NULL
)の代入やゼロ(NULL
)との比較
alloc
, afree
以下のプログラム例での allocbuf
の状態。
#include <stdio.h> #define ALLOCSIZE 10000 /* 使用可能な場所の大きさ */ static char allocbuf[ALLOCSIZE]; /* alloc のための記憶場所 */ static char *allocp = allocbuf; /* 次の空き位置(allocbuf の先頭アドレスを指して初期化) */ char *alloc(int); void afree(char*); int main(void) { int n; char *p, *q; printf("p => %p\n", p); printf("q => %p\n", q); n = 10; p = alloc(n); printf("p => %p\n", p); *p = 'a'; *(p+1) = 'b'; *(p+2) = 'c'; *(p+3) = '\0'; printf("allocbuf => %s\n", allocbuf); /* p で確保した allocbuf の領域が使用されている */ q = alloc(n); printf("q => %p\n", q); *q = 'A'; *(q+1) = 'B'; *(q+2) = 'C'; *(q+3) = '\0'; printf("allocbuf[n] => %s\n", &allocbuf[n]); /* q で確保した allocbuf の領域が使用されている */ afree(p); afree(q); printf("p => %p\n", p); printf("q => %p\n", q); return 0; } /* n 文字へのポインタを返す */ char *alloc(int n) { if (allocbuf + ALLOCSIZE - allocp >= n) { /* 入りきる */ allocp += n; return allocp - n; /* 古い p */ } else { /* 十分な空きがないとき */ return 0; /* 異常事態を表わす 0 、通常は NULL (stdio.h で定義) を使う */ } } /* p によって指される領域を解放する */ void afree(char *p) { if (p >= allocbuf && p < allocbuf + ALLOCSIZE) { allocp = p; } }
実行結果
$ ./alloc p => 0x7fff5fbfebe8 q => 0x0 p => 0x100001080 allocbuf => abc q => 0x10000108a allocbuf[n] => ABC p => 0x100001080 q => 0x10000108a
プログラミング言語C 第2版 ANSI規格準拠
posted with amazlet at 09.11.27
B.W. カーニハン D.M. リッチー
共立出版
売り上げランキング: 9726
共立出版
売り上げランキング: 9726