Нет никакого способа добиться изменчивой семантики значений для элементов переменного размера (семантически, я думаю, что вам нужно, чтобы MyInfo1 = MyInfo2
сгенерировал новый связанный список, который отделен от того, который был запущен MyInfo2) , Можно заменить info?
на info[]
(который всегда будет либо нулевым, либо заполнен одноэлементным массивом), либо классом-держателем, который оборачивает экземпляр info
, но семантика, вероятно, не будь то, что ты после. После MyInfo1 = MyInfo2
изменения на MyInfo1.a
не повлияют на MyInfo2.a
, а изменения на MyInfo1.c
не затронут MyInfo2.c
, но изменения на MyInfo1.c[0].a
повлияют на MyInfo2.c[0].a
.
Было бы неплохо, если бы в будущей версии .net было какое-то понятие «ссылки на значения», чтобы при копировании структуры не просто копировались все ее поля. Существует некоторая ценность того факта, что .net не поддерживает все тонкости конструкторов копирования C ++, но было бы также полезно, чтобы места хранения типа 'struct' имели идентификатор, который был бы связан с местом хранения, а не его содержание.
Учитывая, что .net в настоящее время не поддерживает такую концепцию, однако, если вы хотите, чтобы info
был изменчивым, вам придется либо мириться с изменяемой ссылочной семантикой (включая защитное клонирование), либо со странным и дурацкая семантика гибридного структурного класса. Одно из предложений, которое у меня возникло бы, если бы производительность была проблемой, было бы иметь абстрактный класс InfoBase
с потомками MutableInfo
и ImmutableInfo
и со следующими членами:
AsNewFullyMutable
- Открытый экземпляр - Возвращает новый объект MutableInfo
с данными, скопированными из оригинала, вызывая AsNewFullyMutable
для любых вложенных ссылок.
AsNewMutable
- Открытый экземпляр - Возвращает новый объект MutableInfo
, данные которого копируются из оригинала, вызывая AsImmutable
для любых вложенных ссылок.
AsNewImmutable
- Защищенный экземпляр - Возвращает новый объект ImmutableInfo
с данными, скопированными из оригинала, вызывая AsImmutable
(не AsNewImmutable
) для любых вложенных ссылок.
AsImmutable
- Публичный виртуальный - для ImmutableInfo
верните себя; для MutableInfo
звоните AsNewImmutable
на себя.
AsMutable
- общедоступный виртуальный - для MutableInfo
верните себя; для ImmutableInfo
звоните AsNewMutable
на себя.
При клонировании объекта, в зависимости от того, ожидал ли он, что объект или его потомки будут снова клонированы, прежде чем его нужно будет мутировать, он будет вызывать либо AsImmutable
, AsNewFullyMutable
, либо AsNewMutable
. В сценариях, где можно ожидать, что объект будет многократно клонироваться в целях защиты, этот объект будет заменен неизменным экземпляром, который больше не придется клонировать до тех пор, пока не возникнет желание его мутировать.