На каких правилах C ++ это определение declval на основе? [Дубликат]

28
задан ildjarn 7 February 2013 в 01:32
поделиться

3 ответа

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

Другими словами, это не ошибка. Хотя многие вещи могут быть проверены только после создания экземпляра шаблона, существуют другие проверки достоверности, которые компилятор может выполнить даже раньше. Вот почему, например, C ++ имеет двухфазный поиск имен. Компилятор просто пытается помочь вам найти ошибки, которые на 100% могут возникнуть.

20
ответ дан Andy Prowl 5 September 2018 в 10:00
поделиться

Это действительно комментарий, но для этого нужен пример кода.

Текст священного стандарта для static_assert не ограничивает его действие на экземплярный код.

Однако код

template <typename T>
inline T getValue(int&)
{
    typedef char blah[-1];  // Common C++03 static assert, no special semantics.
}

int main()
{}

также не удается скомпилировать с MinGW g ++ 4.7.2, что подчеркивает вопрос.

I think ответ заключается в том, что g ++ прав, и что Visual C ++ 11.0, который не создает ошибку компиляции для этого, неверен, но мне было бы трудно предоставить соответствующий анализ в терминах стихов Святого Стандарта.

Практическое следствие разница в компиляторе заключается в том, что в настоящее время вы не можете полагаться на поведение.

3
ответ дан Cheers and hth. - Alf 5 September 2018 в 10:00
поделиться

Стандарт говорит в [temp.res] / 8

Диагностика не должна выдаваться для определения шаблона, для которого может быть создана действительная специализация. Если для определения шаблона не может быть создана действительная специализация, и этот шаблон не создается, определение шаблона плохо сформировано, не требуется диагностика. ... [Примечание: Если экземпляр шаблона создается, ошибки будут диагностированы в соответствии с другими правилами настоящего стандарта. Точно, когда эти ошибки диагностируются, это проблема качества реализации. - примечание к концу]

Невозможно создать экземпляр шаблона функции, который будет компилироваться, поэтому определение шаблона плохо сформировано и поэтому разрешен компилятор (но не обязательно), чтобы отклонить его, даже если он не создан.

Вы можете заставить его работать следующим образом:

template<typename T>
struct foobar : std::false_type
{ };

template <typename T>
inline T getValue(AnObject&)
{
    static_assert( foobar<T>::value , "this function has to be implemented for desired type");
}

Теперь компилятор не может сразу отказаться от шаблона функции , поскольку до момента его создания он не знает, будет ли специализация foobar, которая имеет value == true. При создании экземпляра соответствующая специализация foobar<T> будет создана и статическое утверждение будет по-прежнему терпеть неудачу.

42
ответ дан Jonathan Wakely 5 September 2018 в 10:00
поделиться
Другие вопросы по тегам:

Похожие вопросы: