Этот вопрос касается того, что я заметил в спецификации С++, когда я пытался ответить на этот ранее, интригующий вопрос о приведениях в стиле C и преобразования типов.
Спецификация С++ рассказывает о приведениях в стиле C в разделе & section; 5.4. В нем говорится, что нотация заметок будет пытаться выполнить следующие действия в этом порядке до тех пор, пока не будет найдено, что это действительно:
-
const_cast
-
static_cast
-
static_cast
, за которым следуетconst_cast
-
reinterpret_cast
-
reinterpret_cast
, за которым следуетconst_cast
.
Хотя у меня есть отличная интуитивная идея о том, что означает использовать static_cast
, за которым следует const_cast
(например, чтобы преобразовать a const Derived*
в Base*
, пройдя через const_cast<Base*>(static_cast<const Base*>(expr))
), Я не вижу каких-либо формулировок в спецификации, говоря, что, в частности, следует использовать типы, используемые в серии static_cast
/const_cast
. В случае простых указателей это не так сложно, но, как видно из связанного вопроса, приведение может быть успешным, если дополнительный const
вводится в одном месте и удаляется в другом.
Существуют ли какие-либо правила, определяющие, каким образом компилятор должен определить, какие типы использовать в цепочке литья? Если да, то где они? Если нет, является ли это дефектом в языке или существуют достаточные неявные правила, позволяющие однозначно определять все возможные броски, чтобы попробовать?