Подтвердить что ты не робот

Шаблонные объединения в С++ 11

Говорит ли стандарт С++ 11 о шаблонных объединениях? (Я ничего не могу найти в http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2011/n3242.pdf, но я не читал его так тщательно.)

У меня

template<typename T>
union u {
  T a;
  char b;
};

template<typename T>
u<T> make_u(T t) {
  return { .a = t };
}

int main() {
  return make_u<int>(1).a;
}

Этот код заставляет icpc -std=c++11 сказать error: a designator into a template-dependent type is not allowed, g++ -std=c++0x сказать error: expected primary-expression before ‘.’ token и g++ -std=c++11 (версия 4.8.0 (экспериментальный)), чтобы сказать internal compiler error: in lookup_field_1, at cp/search.c:387. Я могу обойти это, заменив { .a = t } на t. Однако я не мог сделать это для полей, которые не являются первым членом союза. Есть ли способ выбрать какой-то член, отличный от первого, в шаблоном союзе, где соответствующий член зависит от шаблона? (Я мог бы, конечно, объявить объединение в стеке и установить член равным требуемому мне значению. Но я не мог сделать этого в списке инициализаторов или в функции constexpr.)

4b9b3361

Ответ 1

Синтаксис { .a = t } - это нестандартное расширение GNU, поэтому его взаимодействие с другими функциями С++ выходит за рамки стандарта С++.

Решение: напишите стандарт С++:

u<T> make_u(T t) {
  u<T> r;
  r.a = t;
  return r;
}

EDIT: AFAIK, в С++ 11, вы можете дать вашему объединению конструктор (constexpr, если хотите), который выполняет инициализацию, в которой вы нуждаетесь. Пример: http://ideone.com/s4GHjU