Я читал книгу Ричарда Ризса (май 2013 г.) книгу О'Рейли "Понимание и использование указателей С", и у меня есть вопрос о некотором коде в ней, на странице 87.
if (++length > maximumLength) {
char *newBuffer = realloc (buffer, maximumLength += sizeIncrement);
if (newBuffer == NULL) {
free (buffer);
return NULL;
}
currentPosition = newBuffer + (currentPosition - buffer);
buffer = newBuffer;
}
Я надеюсь, что имена переменных не требуют пояснений; если контекст необходим, я отредактирую, чтобы предоставить весь фрагмент кода, а не только этот фрагмент.
Мой вопрос о линии currentPosition = newBuffer + (currentPosition - buffer);
. Мое понимание realloc()
заключается в том, что когда новое распределение успешно завершается, изначально выделенная память освобождается. Если это правильно, тогда строка, о которой идет речь, использует оборванные указатели, не так ли? Оба buffer
и currentPosition
в RHS этого выражения являются указателями на память, которые были освобождены.
Моим инстинктом было бы переписать это, чтобы избежать использования оборванных указателей, используя length
, который, в конце концов, уже существует. Я хочу заменить эти последние две строки:
buffer = newBuffer;
currentPosition = buffer + length;
Однако, предположительно, код, написанный, работает, потому что два указателя по-прежнему содержат адреса (хотя и от мусора), а смещение между этими двумя адресами все равно можно рассчитать как способ переназначения currentPosition
. Так что я просто безрассудно чувствую себя неловко?
Чтобы обобщить вопрос: как только указатель свисает, безопасно ли использовать адрес, содержащийся в указателе, для любых целей, например вычисления смещений? Благодарю.