Ответ
Ответ зависит от типа памяти самой структуры, но экземпляр класса всегда хранится в куче (heap).
Механика:
- Структура (
struct) — тип-значение. Если она локальная переменная, то хранится в стеке. Если свойство класса — в куче. - Класс (
class) — ссылочный тип. Его экземпляр всегда создается в куче. - Свойство структуры, имеющее тип класса, содержит не сам объект, а ссылку на него. Эта ссылка хранится вместе со структурой, а объект — отдельно в куче.
Наглядный пример:
class MyClass { var value = 42 }
struct MyStruct { let object = MyClass() } // свойство - ссылка на класс
var structA = MyStruct() // Структура в стеке, MyClass в куче
var structB = structA // Копируется ВСЯ структура (значение), но ссылка `object` в копии указывает на ТОТ ЖЕ объект в куче.
structB.object.value = 10
print(structA.object.value) // 10! Обе структуры разделяют один экземпляр класса.
Вывод: Объект класса живет в куче независимо от контекста. Структура хранит лишь ссылку на него.
Ответ 18+ 🔞
А, ну ты про это, про память в Свифте! Давай разжую, как есть, без соплей.
Смотри, тут всё просто, как три копейки, но есть один подвох, который всех новичков в пизду отправляет. Запоминай раз и навсегда.
Класс (class) — это как твой паспорт. Сам паспорт — это кусок пластика и бумаги, он лежит в одном конкретном месте (в столе, в сейфе). Это куча (heap). У тебя на руках только ксерокс с пометкой «где искать оригинал». Это ссылка. Куда бы ты эту бумажку ни понес — в бар, в ментовку, домой — все будут смотреть по этой пометке в один и тот же сейф. Изменят что-то в оригинале — всем, у кого ксерокс, станет известно. Экземпляр класса всегда, блядь, всегда живёт в куче.
Структура (struct) — это как наличные в кармане. Ты их потрогал — они твои. Передал другу — у тебя в кармане пусто, у него — есть. Это значение. Обычно оно болтается там, где удобно: в стеке вызовов, если это локальная переменная в функции. Но! Если ты эту структуру засунул внутрь класса — то она поедет туда же, куда и класс, то есть в кучу. Потому что она теперь часть того самого паспорта в сейфе.
А теперь главный пиздец, где все путаются:
Допустим, у тебя в структуре есть свойство, которое является... классом! Что хранится в структуре? Сам объект? Нихуя подобного!
Структура хранит ссылку на этот объект. Как та самая бумажка с адресом сейфа. Сама структура может быть в стеке, но объект, на который она ссылается, — он в куче, отдельно, как взрослый дядька.
Вот, смотри, реальный пример, чтобы мозг не взорвался:
class Пиздёныш { var сила = 9000 } // Класс. Живёт в куче.
struct Контейнер { let житель = Пиздёныш() } // Структура. В свойстве — ССЫЛКА на Пиздёныша в куче.
// Создаём структуру. Сама `boxA` — в стеке (условно). Но внутри неё ссылка.
var boxA = Контейнер()
// Копируем структуру. Всё значение копируется, включая ссылку!
var boxB = boxA
// Меняем объект через ссылку в КОПИИ структуры.
boxB.житель.сила = 1
// Смотрим, что стало с объектом в ИСХОДНОЙ структуре.
print(boxA.житель.сила) // Выведет 1, ёпта! Потому что обе ссылки ведут к одному и тому же Пиздёнышу в куче!
Видишь, в чём подвох? Скопировали мы структуру, да. Но скопировали мы значение ссылки, а не сам объект. Обе бумажки с адресом теперь указывают на один и тот же сейф. Полезли через одну бумажку, поменяли содержимое сейфа — все остальные владельцы таких же бумажек охуеют.
Итог, коротко и ясно: Объект класса — всегда в куче. Структура, если в ней есть свойство-класс, хранит не объект, а адресную бумажку на него. Копирование структуры копирует бумажку, а не то, что лежит по адресу. Вот и вся магия, ебать её в сраку.