Ответ 1
Насколько я могу судить, это составной литерал, это функция C99, это не стандартный С++, но и gcc и clang поддерживают его как расширение:
ISO C99 поддерживает сложные литералы. Комбинированный литерал выглядит как листинг, содержащий инициализатор. Его значение является объектом типа, указанного в листинге, содержащего элементы, указанные в инициализаторе; это значение lvalue. В качестве расширения GCC поддерживает сложные литералы в режиме C90 и на С++, хотя семантика несколько отличается на С++.
Обычно указанный тип является структурой. Предположим, что struct foo и Структура объявляется как показано:
struct foo {int a; char b[2];} structure;
Вот пример построения структуры foo с соединением буквальный:
structure = ((struct foo) {x + y, 'a', 0});
Это эквивалентно написанию следующего:
{ struct foo temp = {x + y, 'a', 0}; struct
В этом случае тип a
будет указывать на int. Надеюсь, это был исходный код C, поскольку в документе gcc говорится:
В C составной литерал обозначает неназванный объект со статическим или автоматическим временем хранения. В С++ составной литерал обозначает временный объект, который живет только до конца его полного выражения.
и поэтому использование адреса в С++, вероятно, является плохой идеей, так как время жизни объекта заканчивается в конце полного выражения. Хотя, возможно, это был код С++, который просто полагался на поведение undefined.
Это один из тех случаев, когда использование правильных флагов действительно очень помогает, как в gcc, так и в clang, используя - pedantic будет создавать предупреждение и ошибка, например gcc говорит:
warning: ISO C++ forbids compound-literals [-Wpedantic]
auto a = &(int) { 1 };
^
error: taking address of temporary [-fpermissive]
если мы используем -fpermissive
, это gcc, это действительно позволяет компилировать этот код. Я не могу заставить clang создать этот код с любыми флагами в современных версиях, хотя старые версии, похоже, позволяют использовать его -Wno-address-of-temporary
. Интересно, может ли gcc использовать это как остаток старого расширения.
Обратите внимание, что вопрос Cryptic struct definition в C имеет довольно интересное (в зависимости от вашего определения интересное) использование сложных литералов.
Предполагая, что раскол верен и этот вопрос является исходным источником, а затем используется в этом коде в пример:
if (setsockopt(server_connection.socket, SOL_SOCKET, SO_REUSEADDR, &(int) { 1 }, sizeof(int)) < 0) {
является допустимым использованием как на C99, так и на С++.