Что беспокоит разработчика библиотеки С++ std, чтобы предупредить неопределенное поведение при добавлении специализации для шаблона remove_cvref?

В этой ссылке https://en.cppreference.com/w/cpp/types/remove_cvref указано

      template< class T >
struct remove_cvref;

Если тип T является ссылочным типом, предоставляет тип typedef члена, который является типом, на который ссылается T, с удаленными его самыми верхними квалификаторами cv. В противном случае типом является T с удаленными самыми верхними квалификаторами cv.

Поведение программы, добавляющей специализации для remove_cvrefне определено.

Что беспокоит разработчика библиотеки C++ std в этом случае?

1 ответ

Стандарт C++ запрещает специализацию почти любого из шаблонов признаков типа C++. Причина этого в том, что черты типа должны быть низкоуровневыми, базовыми конструкциями, которые делают точно и только то, что говорят. Это означает, что пользователям не должно быть позволено тянуть с собой обычные махинации, заменяя их функциональность тем, что они хотят.

Допустим, вы находитесь в функции шаблона с некоторым типом параметра шаблона. И вы хотите условно выполнить какой-то код, если он является файлом . Но этот код будет работать нормально, если является или или что-то еще. Вы просто хотите увидеть, предоставил ли пользователь тип.

Ты используешь получить как тип, то это против . Это может работать, только если делает точно и только то, что он говорит, что делает. Если пользователь может специализировать его, то он может солгать вам, сделав свой пользовательский тип похожим на и тем самым сломать ваш код.

Думайте о признаках типов в C++ как о языковых операциях с типами, которые определены в заголовке, а не всегда присутствуют. По всем правилам C++ должен иметь оператор, который преобразует тип в версию с удаленным cvref. Вместо выделенного оператора у нас есть метафункции признаков типа. Но независимо от того, как она определена, это по-прежнему фундаментальная операция, смысл которой нельзя изменить.

Другие вопросы по тегам