У меня есть несколько проектов, которые широко используют boost::shared_ptr
или std::shared_ptr
(я могу достаточно скоро перейти на любую из этих реализаций, если для одного есть хороший ответ на этот вопрос, но не для другого). Реализация Boost использует Boost.Assert, чтобы избежать возврата в случае обнаружения пустого (NULL) указателя в operator*
или operator->
во время выполнения; в то время как реализация libc++, похоже, не проверяет.
Хотя, конечно, правильность shared_ptr
должна быть проверена перед использованием, большая кодовая база со смешанной парадигмой заставляет меня хотеть попробовать вариант, выбрасывающий исключения; так как большая часть кода относительно осведомлена об исключениях и в лучшем случае перейдет в высокоуровневое, но возобновляемое состояние, а не в std::terminate()
или segfault.
Как лучше всего настроить эти средства доступа, сохранив при этом надежность shared_ptr
? Кажется, что инкапсуляция shared_ptr
в throwing_shared_ptr
может быть лучшим вариантом, но я опасаюсь нарушить магию. Лучше ли мне скопировать исходный код Boost и просто изменить ASSERT
s на соответствующий оператор throw
?
Фактическое имя типа, используемое везде для соответствующего типа smart_ptr<T>
, представляет собой определение типа, расширенное из макроса; то есть ForwardDeclarePtr(Class)
расширяется до чего-то вроде:
class Class;
typedef boost::smart_ptr<Class> ClassPtr;
Все проходит, принимает или сохраняет ClassPtr
, так что я могу довольно свободно заменить базовый тип; и я подозреваю, что это устраняет потенциальную проблему нарезки/скрытия.