経由でメモリを再割り当てするrealloc()
と、以前の内容は上書きされますか? データを入力するたびにメモリを再割り当てするプログラムを作成しようとしています。
realloc によるメモリ割り当てについて教えてください。たとえば、コンパイラに依存しますか?
古い内容は気にしないでください。
使用する正しい方法realloc
は、再割り当てに特定のポインターを使用し、そのポインターをテストし、すべてがうまくいった場合は古いポインターを変更することです
int *oldpointer = malloc(100);
/* ... */
int *newpointer = realloc(oldpointer, 1000);
if (newpointer == NULL) {
/* problems!!!! */
/* tell the user to stop playing DOOM and retry */
/* or free(oldpointer) and abort, or whatever */
} else {
/* everything ok */
/* `newpointer` now points to a new memory block with the contents of oldpointer */
/* `oldpointer` points to an invalid address */
oldpointer = newpointer;
/* oldpointer points to the correct address */
/* the contents at oldpointer have been copied while realloc did its thing */
/* if the new size is smaller than the old size, some data was lost */
}
/* ... */
/* don't forget to `free(oldpointer);` at some time */
既存のコンテンツを上書きせずに、既に割り当てられているメモリを拡張するか、または (拡張できない場合) 新しいより大きなメモリを別の場所に割り当て、既存のコンテンツを以前のメモリから新しいメモリにコピーします。
はい、古いポインターが上書きされているかのようにプログラムする必要があります。古いメモリは割り当てられなくなったため、プログラムの別の部分 (またはシステム スレッドなど) によって再割り当てされ、realloc を呼び出した後はいつでも上書きできます。
ただし、新しいメモリには常に古いメモリに存在していたのと同じデータが含まれますが (必要に応じてコピーされます)、古いブロックのサイズまでのみ、最後に割り当てられた余分なスペースは初期化されません。
コピーが必要な場合は、新しい malloc を実行して memcpy を使用します。
実装に関しては、サイズを増やすためにrealloc を呼び出すと、次のいずれかが発生する可能性があります。
何が起こったのかを知る方法がないため、または上記で提案したものとはまったく異なる実装が使用されている場合でも、常に realloc の仕様に従ってコーディングする必要があります。つまり、古いポインターを使用してはならず、新しいものを使用する必要があります。
何を尋ねているのかわかりにくいですが、 に渡された古いアドレスの「古いコンテンツ」を読めるかどうかを尋ねている場合realloc
、答えはnoです。場合によっては、古いコンテンツの一部またはすべてがそこにあるかもしれませんが、realloc
渡したのと同じポインターが返されない限り、古いポインターの使用は未定義の動作です。
によって返される新しいアドレスに古いコンテンツが保存されるかどうかを単に尋ねている場合realloc
、答えはイエスです (古いサイズと新しいサイズの最小値まで)。