О молодец, но за деревьями не видишь леса а что не привел, что значит type-id? which is syntactically a declaration for an object or function of that type that omits the name of the object or function. Суть в том, что это декларация function type. Я этот пример не сам придумал, а скопировал из 8.3.5 =) The type of a function is determined using the following rules. бла бла бла. After producing the list of parameter types, several transformations take place upon these types to determine the function type. Any cv-qualifier modifying a parameter type is deleted. [Example: the type void(*)(const int) becomes void(*)(int) —end example] struct S; // S имя типа 3/5 здорово приплел, но мимо. не смущает, что там не Every declaration introduses... ? читай уж следом: 3/6 Some names denote types, classes, enumerations, or templates. Ооо а дальше то: In general, it is necessary to determine whether or not a name denotes one of these entities before parsing the program that contains it. Надо, оказывается, распарсить что такое F перед * Вообще про декларации читать надо 7 главу. Declarations specify how names are to be interpreted. Декларация _всегда_ вводит имя - это где написано? Не смущает наличие анонимных неймспейсов, или замыканий в новом стандарте, чем тип хуже? С чего ты взял, что я утверждаю это? decl-specifier-seq (что значит "последовательность спецификаторов декларации", opt щас поставил в скобочки, значит опционально) входящий в simple-declaration рекурсивен. Такой рекурсивынй decl-specifier-seq можно заменить цепочкой simple-declaration, это обычная практика, когда сложный compound type (это не масло масленное, а я подчеркиваю особую сложность типа) вводится путем серии typedef. Когда компайлер парсит это в АСТ, для него не будет разницы с decl-specifier-seq, за исключением того, что имена типов введенные typedef будут явными, а без него - анонимными. Это я подразумевал под одинаковой семантикой. Очевидно, что ты пытаешься строить доказательства на отрицании не имеющих отношения к делу вещей, вроде общих случаев. То, что может присутствовать в декларации, определено в синтаксисе и вообще: the components of a decl-specifier-seq, are described in 7.1 and declarators, the components of an init-declarator-list, are described in clause 8. 3/3 же говорит об An entity, а не введенном определением имени (имеешь ввиду имена объявляемый внутри определения функции, что ли? =)) Я с этого примера начинал предыдущий пост, и в этом посте самый первый код. Просил же тебя разобраться с: 8.3.5/1 In a declarationT D where D has the form D1 ( parameter-declaration-clause ) cv-qualifier-seqopt exception-specificationopt and the type of the contained declarator-id in the declaration T D1 is “derived-declarator-type-list T,” the type of the declarator-id in D is “derived-declarator-type-list function of (parameter-declaration-clause) cv-qualifier-seqopt returning T”; a type of this form is a function type. Это не декларация функции, а декларация имеющая функциональный тип. Она может быть объявлением функции, а может и не быть. Ты, вместо того, что бы разобраться в смысле этих слов начал цепляться к ненормативности Notes & Examples. да они не определяют правила в стандарт, они даны, что бы лучше и проще его могли понять. Соль не в "cv-qualifier", а в "the function type to which a pointer to member refers, or the top-level function type of a function typedef declaration". Ты ведь не захотел подумать, о чем я просил в #70? Так вот напрасно, это бы избавило тебя от вопросов не по теме. P.S. Заметь, упоминая сказанное "читай стандарт", я не имел ввиду лично тебя, поскольку ты как раз приводишь конкретные пункты, которые надо читать, а это я приравниваю к цитированию стандарта. Я говорил в том числе о соседних топиках, где видимо предлагалось читать его весь целиком.) Вместо этого я бы мог указать что ты "надергал из стандарта куски", но до сих пор не обвиняю тебя в переходе на личности Я уже объяснял, мне личности не важны. А вот ты что-то сильно близко к сердцу все воспринимаешь, это мешает трезво поразмыслить над №70.
А есть ли баг в Камю? тут скорее коллизия в стандарте. 8.3.5/7!=14.3.1/3 согласно 8.3.5/7 это разрешено
J0E Понятие множества слишком абстрактно, чтобы утверждать что "никакого множества объектов в языке С++ нет". Я просто пытался дать определение типа. Если тебе известно лучшее определение, интересно было бы увидеть. Утверждения типа определением, конечно, не являются. Впрочем это уже чисто академические рассуждения. Практически важно то, что п. 14.3.1 стандарта неприменим к typedef-декларациям. Т.е. Код (Text): typedef F F_t; в приведённом шаблоне не является ill-formed, согласен?
RedLord Формально получается баг, т.к. Комо компилит такой код: Код (Text): template<class T> void f(){ T t; // ill-formed согласно п. 14.3.1/3 } Не совсем понимаю, в чём состоит коллизия. 8.3.5/7 вводит "нефункциональные" декларации ф-ций вообще, а 14.3.1/3 ограничивает их использование в шаблонах.
Исправление предыдущего поста. RedLord Формально получается баг, т.к. Комо компилит такой код: Код (Text): template<class T> void f(){ T t; // ill-formed при последующей инстанциации, согласно п. 14.3.1/3 } template void f<void()>(); Не совсем понимаю, в чём состоит коллизия. 8.3.5/7 вводит "нефункциональные" декларации ф-ций вообще, а 14.3.1/3 ограничивает их использование в шаблонах.
Попался (ты) Точка с запятой там вобщето не к месту - с ней будет ill-formed, т.к. не ни одна из форм top-level деклараций не может состоять (только) из type-id. Ну так в чем проблемы: To specify type conversions explicitly, and as an argument of sizeof, new, or typeid, the name of a type shall be specified. This can be done with a type-id, which is syntactically a declaration for an object or function of that type that omits the name of the object or function. ... Презабавный пример поскипан... It is possible to identify uniquely the location in the abstract-declarator where the identifier would appear if the construction were a declarator in a declaration. The named type is then the same as the type of the hypothetical identifier. Обрати внимание на выделенное (и на грамматику из 8.1/1) - type-id представляет собой тип, который имел бы некоторый гипотетический идентификатор, в чьей декларации участвует этот тип. В том самом забавном примере примере ты можешь увидеть наглядное подтверждение этому (только вот не надо приписывать точки с запятой). Слева - type-id, справа декларация некого объекта. Сам по себе type-id не включает имя объекта. Что - это? Если это - 'void(*)(const int);' то это ill-formed. Если это(упрощу) 'void(*p)(int);', то начала покажи грамматику, согласно которой формируется эта конструкция. Полностью, начиная c 'simple-declaration'. Во первых ты приписал сюда точку с запятой и обозвал выражением. Согласись, это не имеет ничего общего с примером, в котором показано удаление cv-квалификатора из типа параметра перед определением (всмысле вяснения) function type. Логика такая: что бы говорить что 'S' является именем типа, необходимо чтобы имя 'S' было обявлено. И только после этого, основываясь на форме объявления можно сказать чем все-таки является 'S'. 3/5 вводит определения понятия 'declaration'. Мимо не может быть в принципе. Совершенно не смущает. Про 'рапарсить F' - это твои домыслы. Здесь написано, что перед парсингом конструкции, содержащей _имя_, нужно определить сущность, которую обозначает это самое имя (в примере - это параметр шаблона). Это ты придумал. Забавно. Ошибся - в твоих словах я увидел 'decl-specifier-seq' там где находтся 'declaration-seq'. Но вот теперь ниже ты явно это утверждаешь (см. выделенное): decl-specifier-seq не может содержать simple-declaration. Тем не менее фраза 'в декларации присутствует тип' остается неверной. Прочитай еще раз про 'рапарсить F' выше. Видишь упоминание 'declarator-id' ? Это ничто иное как _имя_ функции. Имя должно присутстовать обязательно, а это значит что такая декларация не может иметь вид type-id, хотя это и так понятно. ЧТД. Осталось добавить 7/5: Просто не надо было ссылаться на них как на нормативный текст. Это все-таки мимо. И зачем ты обрезал первую часть предложения? Этот пункт определяет места возможных вхождений cv-квалификаторов (+ дополнительно к этому существуют другие ограничения): 8.3.5/4 A cv-qualifier-seq shall only be part of // the function type for a nonstatic member function struct X { void f() const; } // the function type to which a pointer to member refers, void (X::*)() const // or the [part of] top-level function type of a function typedef declaration typedef void F() const; 'Соли' я тут не вижу... Ок, что у нас в #70: Это? Ты почему-то сразу рассматриваешь случай 'после инстациирования', хотя есть еще и до: 14.6/7 Но в данном случае можно представить такой тип, инстанцирование которым не приведет к ошибке, поэтому без инстанцирования 'no diagnostic shall be issued'. Нет. Как раз таки 14.3.1/3 говорит о том, что ошибка должна быть в 0*. Верно. Еще один валидный вариант: T представляет собой class-type с соответствующими операторами (такими что 0*, 1* и 2* оказываются допустимыми). см. выше. Это не имеет значения - до инстанцирования можно выяснить что 'valid specialization can be generated'. Что там дальше получится - будет ясно только при инстанцировании. agreed.
ответ Адамчика из EDG. A typedef to any type is valid, including a typedef to a function type, so there's nothing wrong with In a function body, a declaration of something with a function type is an extern declaration of a function (a block extern declaration). is the same as extern int t();
RedLord Это-то понятно. Но тем не менее - формальное расхождение со Стандартом. Хотя в данном случае логичнеее было бы внести правку в Стандарт чем в Комо, т.к. ограничение 14.3.1/3 для функциональных шаблонов совершенно необосновано.
По поводу typedef F F_t; // ill-formed??????????????? Само это выражение, в общем виде, не обязательно ill-formed. Оно таковым становится при инстанциации шаблона, кода F функциональный тип. "I submitted a reduced version of the code to Comeau and asked them why it didn't compile. It turns out to be 14.3.1/3:" http://www.rhinocerus.net/forum/language-c-moderated/80676-zero-size-members-templates.html
Соглашусь. Понимаешь в чем дело. Я допускаю ошибки в деталях, ты опровергаешь эти детали. Опровергнув деталь, ты считаешь, что опроверг мое утверждение целиком (формально оно становится неверным). Но сама мысль, которую я хочу донести своими словами заключается в другом: в остальной части, без semicolon. Тебе даже не приходит в голову рассмотреть это выражение (не в терминах С++, понимай под этим запись закорючек, подобно математике) исправив мелкую ошибку. Вместо этого куча флуда но полстраницы. struct {} object_of_anonymous_type; Какой же тип имеет object_of_anonymous_type, если не задекларированный struct {} ? Не может согласно синтаксиса. В выделенном речь о СЕМАНТИКЕ, причем писалось это ЯВНО. Вижу в: тип "of the declarator-id in D" - бла-бла функция. То есть "function type" в 14.3.1/3 значит "бла-бла функция" или "функциональный тип", а не (возвращаемый) тип функции в "type of this form is a function type", где пропущено слово return из сноски ниже. И этот функциональный тип используется в отличном по синтаксису от 8.3.5/1 declaration, что и запрещает 14.3.1/3 По поводу #70 отпишу позже, и так пост целые сутки не мог отправить по хттпс )
green к сожалению не так. это баг. EDG признал это. видимо первый ответ писали на коленке, но пример убедил их: template<class T> void f(){ T t; } typedef int function(); S<function> a; int main() { f<function>(); t - декларация f<int>(); t - локальная переменная } неожиданный поворот
RedLord Вах, исторический момент! Интересно было бы узнать мнение EDG насчёт подоплеки п. 14.3.1/3. Если имеешь возможность - спроси, пожалуйста. J0E, обрати внимание - твой баг в Comeau официально подтверждён.