Догадываясь, почему вы можете быть смущены, я хотел бы добавить объяснение того, что на самом деле делает второй пример кода (и почему это не нужно).
NSMutableDictionary *foo = [[NSMutableDictionary alloc] initWithCapacity:0];
Я думаю, что вы запутались в этой строке, потому что эта строка часто описывается как "инициализация foo". Это немного вводит в заблуждение. С технической точки зрения, здесь изменяются 2 разных объекта - создается новый объект NSMutableDictionary
, а переменной "foo" назначается его адрес.
Строка фактически создает новый объект NSMutableDictionary
в куче (область динамической памяти вашего приложения). Я назову это «Словарь 1». Чтобы найти этот новый объект «Словарь 1» в куче, его адрес памяти сохраняется в «foo». Роль "foo" заключается в том, чтобы выступать в качестве индекса, поэтому мы можем найти "Словарь 1".
Хотя мы часто говорим: «foo - это словарь», это потому, что мы ленивы - это утверждение технически неверно. Правильно: «в куче есть словарь, и foo хранит адрес своей памяти, чтобы мы могли его найти и использовать».
Когда вы запускаете строку:
foo = [bar mutableCopy];
вы используете адрес в "баре", чтобы найти другой объект (я назову его "Словарь 2") в куче, и сделать еще один объект ("Словарь 3") в куче с теми же значениями , Если вы ведете счет, то теперь существует 3 объекта.
После того как "Словарь 3" создан, его адрес в памяти затем сохраняется в переменной "foo". Это сохранение в «foo» перезаписывает существующий адрес памяти (тот, который указывал на «Словарь 1»). Это означает, что у нас нет оставшихся указателей на «Словарь 1» и, следовательно, мы никогда не сможем найти его снова. Вот почему мы говорим, что «Словарь 1» просочился.
Я надеюсь, что из этой ситуации вы можете понять, почему «Словарь 1» никогда не был нужен (вы когда-либо намеревались использовать «foo» для доступа к копии, «Словарь 3»).