Вы можете использовать структуру в стеке. Это имеет детерминированное разрушение.Вы даже можете пересчитать его, используя std.typecons.RefCounting .Не используйте структуру в куче, если хотите гарантировать, что деструктор работает.На данный момент, я не думаю, что деструкторы структур когда-либо запускаются, если их помещают в кучу, потому что GC не имеет информации, которая ему необходима для этого (это должно быть исправлено в какой-то момент вхотя будущее).
Но если вы настаиваете на том, чтобы поместить его в кучу в классе, и хотите явно уничтожить объект, то вы можете вызвать clear
для него:
clear(obj);
Это вызовет деструктор объекта, а затем переведет его в недопустимое состояние, и все, что попытается использовать его после этого, должно взорваться (IIRC, виртуальная таблица обнуляется).Но память на самом деле не освобождена.Это работа GC.И не используйте delete
.Это будет устаревшим.Я на самом деле удивлен, что этого еще не было, так как было запланировано целую вечность, чтобы избавиться от него.
И, конечно, одним из вариантов является наличие явной функции, которую вы вызываете для освобождения ресурсов,Хорошая идея или нет, зависит от того, что вы делаете.Но независимо от того, классы предназначены для сбора GC и не освобождаются всякий раз, когда вы решите.
Работа выполняется на пользовательских распределителях, что даст вам больше возможностей для того, как распределить класс, и одиниз них, вероятно, вы сможете получить более детерминированное уничтожение классов, но это еще не готово.
А если вы чувствуете себя сумасшедшим, вы можете использовать std.typecons.scoped , которыйзаменяет устаревший модификатор типа scope
(хотя scope
остается в других контекстах - таких как операторы scope
).Он помещает класс в стек.Но это небезопасно (именно поэтому scope
уходит в этом контексте), и вы, вероятно, с таким же успехом можете просто использовать структуру, если вы собираетесь поместить объект в стек.
РЕДАКТИРОВАТЬ: Вы также можете использовать malloc
и free
с std.conv.emplace , чтобы поместить объект в выделенный кусок памяти без GC, как в C ++, ноЯ думаю, что вам придется явно вызывать деструктор, чтобы запустить его, так как free
не понимает деструкторов (это C-функция).Это имело бы преимущество в том, что память уходила вместе с ресурсом (тогда как использование clear
для объекта в куче ГХ просто уничтожило бы содержимое объекта, а не освободило память), но я не знаю, что это покупаетвы намного больше используете clear
для объекта, выделенного GC.
Однако вы можете создать бесплатную функцию, аналогичную new
, которая выполняет для вас malloc
и emplace
, и затем иметьбесплатная функция, похожая на delete
, которая вызывает деструктор, и free
, которая даст вам ту же ситуацию, что и C ++.На самом деле, мне интересно, будет ли это достаточно полезно, чтобы включить его в стандартную библиотеку.Это, вероятно, такая вещь, которая в конечном итоге в пользовательских распределителей, хотя.Поэтому меня совсем не удивит, если в относительно ближайшем будущем вы сможете использовать собственный распределитель для выполнения чего-то вроде
auto obj = customAllocObj.create!MyObj(args);
//Do stuff...
customAllocObj.destroy(obj);
И я думаю, что это решит вашу проблему довольно хорошо, учитывая, чтоПо сути, это то же самое, что и в C ++, только с библиотечными функциями, а не со встроенными new
и delete
.Я думаю, что я подниму это в группе новостей.Я ожидаю, что есть, по крайней мере, некоторые люди, которые хотели бы такую функцию, и это, кажется, хорошо вписывается в пользовательские распределители.