C ++ 11 — шаблонная эквивалентность C ++ прототипов

Следующие компиляции запускаются и выполняются, как и ожидалось:

#include <cstdlib>
#include <cstring>
#include <iostream>
#include <type_traits>

class Freaky {
public:
template<
typename UNSIGNED_TYPE,
typename std::enable_if<(sizeof(UNSIGNED_TYPE)>=sizeof(int)),int>::type X = 0
>
static UNSIGNED_TYPE copyThing(int  x) ;
};

template<
typename UNSIGNED_TYPE,
typename std::enable_if<(sizeof(UNSIGNED_TYPE)>=sizeof(int)),int>::type X
>
UNSIGNED_TYPE Freaky::copyThing(int x) {
UNSIGNED_TYPE r(0);
std::memcpy(&r,&x,sizeof(int));//Please ignore. Not the point of the question...
return r;
}

int main(int argc, char*argv[]) {
std::cout << "The answer is ... " <<
Freaky::copyThing<unsigned long>(10)<<std::endl;
return EXIT_SUCCESS;
}

Вывод образца (фактический вывод может зависеть от порядкового номера и целочисленных размеров):

The answer is .... 10

Следующее не скомпилируется и жалуется на прототип для реализации copyThing() не соответствует заявленному в классе.

#include <cstdlib>
#include <cstring>
#include <iostream>
#include <type_traits>

class Freaky {
public:
template<
typename UNSIGNED_TYPE,
typename std::enable_if<(sizeof(UNSIGNED_TYPE)>=sizeof(int)),int>::type X = 0
>
static UNSIGNED_TYPE copyThing(int  x) ;
};

template<
typename UNSIGNED_TYPE,
typename std::enable_if<(sizeof(int)<=sizeof(UNSIGNED_TYPE)),int>::type X
>
UNSIGNED_TYPE Freaky::copyThing(int x) {
UNSIGNED_TYPE r(0);
std::memcpy(&r,&x,sizeof(int));//Please ignore. Not the point of the question...
return r;
}

int main(int argc, char*argv[]) {
std::cout << "The answer is ... " <<
Freaky::copyThing<unsigned long>(10)<<std::endl;
return EXIT_SUCCESS;
}

Единственная разница между ними состоит в том, что sizeof(UNSIGNED_TYPE)>=sizeof(int) был заменен на sizeof(int)<=sizeof(UNSIGNED_TYPE) в этой реализации.

Очевидно, что два утверждения семантически эквивалент.
Где я могу найти формальное определение того, как прототипы шаблонов определяются как равные?

Это явно некоторый уровень лексической эквивалентности, а не семантической эквивалентности.

1

Решение

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

Компиляторы фактически следуют правилам переопределения шаблона функции, как указано в C ++ 11 14.5.6.1/5+6:

5 Рассматриваются два выражения с параметрами шаблона. эквивалент если два определения функции, содержащие выражения, удовлетворяют одному правилу определения (3.2), за исключением [переименование параметра шаблона].
6 Два функциональных шаблона эквивалент если они объявлены в одной и той же области видимости, имеют одинаковое имя, идентичные списки параметров шаблона и имеют возвращаемые типы и списки параметров, которые эквивалентны с использованием правил, описанных выше, для сравнения выражений, включающих параметры шаблона.

Однако я не могу найти ни одного правила, которое бы применило это к выражениям в типах нетиповых параметров шаблонов для переопределений шаблонов классов.

2

Другие решения


По вопросам рекламы [email protected]