Стандартный мандат enable_shared_from_this должен быть унаследован публично? Зачем?

Распространено наследование отenable_shared_from_this просто чтобы иметь возможность вернутьсяshared_ptrиз функций-членов в качестве основного намерения, без намерения разоблаченияenable_shared_from_this API в производном классе.

Так как использоватьenable_shared_from_this нужно делать это через публичное наследование (предписывает ли стандарт это? каково обоснование?), этого нельзя достичь иenable_shared_from_this API принудительно входит в публичный API производного класса.

Inherentingenable_shared_from_this в частном порядке и делаяshared_ptr класс друга работает на clang в сочетании с libc ++, но не работает с stdlibc ++.

посколькуprivate enable_shared_from_this + friend shared_ptr (или защищенное наследование), по-видимому, покрывает этот вариант использования, разве этого не должно быть достаточно по стандарту для подгонки в качестве решения проблемы «общего от этого»?

 pepper_chico03 июл. 2016 г., 03:38
@ChrisBeck, вот почему я упоминаю, что был другомstd::shared_ptr.
 pepper_chico03 июл. 2016 г., 03:28
@ChrisBeck хорошо, спасибо. Я думаю, что вопрос все еще остается, хотя, если кто-то не хочет делать даже это (protected).
 Chris Beck03 июл. 2016 г., 03:26
Вы можете попробовать наследоватьprotectedт.е.class T : protected std::enable_shared_from_this<T> { ... }; ? Я сам не пробовал
 pepper_chico03 июл. 2016 г., 04:16
@ChrisBeck хорошо. Для меня это лучший дизайн, но сейчас это будет серьезное изменение: - /
 Chris Beck03 июл. 2016 г., 03:47
Хорошо, но тогда вам может понадобиться другstd::make_shared а такжеstd::weak_ptr и другие вещи потенциально
 Chris Beck03 июл. 2016 г., 03:32
Я думаю, что нет никакого способаshared_from_this Механизм может работать, если наследование является полностью частным. То, как это работает, если я правильно понимаю, это то, что структура управления дляshared_ptr (счетчик ссылок) хранится в префиксе вашего класса, так что, например, есть некоторый элемент данных вstd::enable_shared_from_this<T>, Для того, чтобы сделатьshared_ptr отthis, это должно быть в состоянии статического приведенияthis и найти счетчик ссылок. Такжеstd::make_shared нужно уметь обнаруживать подобные вещи в своем типе. Если наследство является частным, то, я думаю, они не могут этого сделать. Точно сказать не могу..
 Chris Beck03 июл. 2016 г., 03:51
Вы знаете, это довольно хороший вопрос, я думаю, я не вижу веской причиныshared_from_this() не стандартизирован как защищенный членstd::enable_shared_from_this, Тогда, если вы хотите обнародовать его, вы можете поставитьusing декларация. Это проще, чем вся эта дружба.

Ответы на вопрос(1)

посколькуprivate enable_shared_from_this + другshared_ptr кажется, охватывает этот вариант использования, разве этого не должно быть достаточно по стандарту?

Нет. Стандарт допускает широкую реализацию того, как они реализуют вещи. Конструкторshared_ptr<T> то, что принимает объект, может отложить материал shared-from-this некоторой вспомогательной функции или другому объекту. Для максимальной иронии, это может отнести к базовому классуshared_ptr<T> ;)

В качестве таких,enable_shared_from_this должен быть доступен по любому коду дляshared_ptr конструктор для работы.

 Nicol Bolas03 июл. 2016 г., 04:27
@pepper_chico: вам придется встать в очередь за всеми, кто пытается получить указатели на функции / указатели на элементы стандартных функций библиотеки.
 pepper_chico03 июл. 2016 г., 04:27
Выглядит как компромисс, позволяющий реализации в широких широтах в ущерб общедоступному API каждого пользователя и слегка ограничивающим его из-за параметров пользовательского API
 lorro04 нояб. 2016 г., 00:29
@NicolBolas:ideone.com/cpzAhH : удалить комментарии вокругprivate чтобы увидеть сообщение об ошибке
 curiousguy11 июн. 2018 г., 02:00
@NicolBolas Обратите внимание, что неполный тип класса все еще может быть производным типом: в определении производного класса он уже является производным типом при определении членов.
 Nicol Bolas28 окт. 2016 г., 17:30
@lorro: Потому что ты не можешь этого сделать. В то время, когдаenable_shared_from_this<T> создается с конкретнымTименно этотT являетсянеполный, В конце концов,T происходит отenable_shared_from_this<T>, право? Поэтому, когда это создается, единственное, что знает компиляторT в том, что имя существует. Функции-членыenable_shared_from_this может получить доступTопределение из-за того, как C ++ определяет, как работают встроенные функции-члены. Но эти правила работают только для членов; вы не можете static_assert для свойстваT в самом классе.
 lorro13 июл. 2016 г., 19:22
Итак, почему неenable_shared_from_this<T> заставить это публичный базовый классT, то есть,T* конвертируется вenable_shared_from_this<T>*? Я мог бы представить ошибку во время компиляции, когда это не удается ..

Ваш ответ на вопрос