#c #arrays #pointers
#c #массивы #указатели
Вопрос:
Я ищу кого-нибудь, кто исправит мое понимание указателей и массивов.
Допустим, у меня есть два массива:
int* array1 = new int[10];
int* array2 = new int[10]{ 1,2,3,4,5,6,7,8,9,10 };
Когда я это делаю array1 = array2
, я получаю следующие значения адресов:
array1: 0000027964C831D0
array2: 0000027964C831D0
amp;array1[0]: 0000027964C831D0
amp;array2[0]: 0000027964C831D0
Когда я это делаю for (size_t i = 0; i < 10; i ) { array1[i] = array2[i]; }
, я получаю:
array1: 0000027964C832B0
array2: 0000027964C83710
amp;array1[0]: 0000027964C832B0
amp;array2[0]: 0000027964C83710
Первый случай (без цикла) имеет смысл для меня. Я присваиваю адрес массива в array2 array1, так что теперь у меня есть два разных указателя, указывающих на один и тот же массив (или, точнее, array2[0] ), следовательно, amp;array1[0] и amp;array2[0] одинаковы.
Но во втором случае (цикл) с самого начала указатели имеют разные адреса. Правильно ли я говорю, что цикл for создал копию массива? Хотя для меня это звучит неправильно.
Комментарии:
1. Цикл копировал значения из одного массива в другой. У вас уже было 2 массива для начала (из-за
new int[10];
инициализации)2. @UnholySheep Спасибо за комментарий. Вот что я тогда понимаю. В первом случае array1 указывает на array2, и если я не удалю перед выполнением array1 = array2, произойдет утечка памяти. Во втором случае все значения array2 просто копируются в array1. Так что, даже если я не удаляю перед циклом, утечки памяти нет?
3. В первом случае
array1
иarray2
являются указателями. Во втором случае вы активно копируете по значению. Редактировать: удалено ненужное использование «по существу»4. @Aditya Не только «по существу» — они являются указателями.
5. @molbdnilo ненужное использование слов было плохой привычкой для me…my плохой лол
Ответ №1:
Указатели — это адреса. Думайте о них как о листках бумаги с написанным на них домашним адресом.
int* array = new int[10];
строит строку из 10 домов ( new int[10]
), затем записывает, где находятся эти дома, и сохраняет адрес array
.
Сказать array
, что это массив, — это проблема, которая вас смутит. Он ошибочно принимает адрес дома за дом. Лист бумаги с надписью 123 road street
«это не мой дом», даже если он однозначно называет мой дом.
Ошибочно принять карту за территорию действительно легко и приводит к путанице. Вам нужно проделать некоторую работу, чтобы распутать это.
array1=array2
берет листок бумаги array1
и записывает на нем адрес 2-го блока домов. Он ничего не делает с домами. Они все еще существуют, но у вас может больше не быть записи о том, где они находятся. Так что теперь они станут заброшенными и потерянными (это называется утечкой памяти).
array1[0] = array2[0]
берем вызванный лист бумаги array2
, идем по указанному на нем адресу и смотрим на первый дом там (он же 0
). Затем он вытаскивает сканер и сканирует весь дом.
Затем вы переходите к месту array1
, где говорится, что есть ряд домов. Вы идете в первый дом (он же 0
) и вытаскиваете свой сканер. Вы переключаете переключатель с сканирования на печать и нацеливаете его на дом.
Он продолжает уничтожать находящийся там дом и распечатывает копию дома, который вы отсканировали, в блоке с именем by array2
.
Затем вы возвращаетесь к блоку с именем by array2
, сканируете array2[1]
2-й дом в блоке, возвращаетесь и печатаете его поверх array1[1]
второго дома в первом блоке.
Это совсем, совсем другая операция, чем царапать адрес блока на листе бумаги и заменять его.
Теперь amp;array1[0]
переходим к блоку с именем by array1
, переходим к первому дому [0]
, затем читаем адрес, написанный на нем ( amp;
) . Поскольку мы называем блоки по адресу первого дома, получается, что это соответствует тому, что мы записали в array1
себе.
array1[1]
будет иметь другой адрес — amp;array1[0]
— но он будет по соседству array1[0]
.