Что возвращает sizeof (имя функции)?

Образец кода:

main ()
{
printf ("size = %d\n", sizeof (main));
}

4 ответа

Стандарт C запрещает это - при компиляции с gcc -pedantic, он производит invalid application of ‘sizeof’ to a function type предупреждение.

тем не мение gcc компилирует и возвращает 1 за sizeof(main)и это не размер указателя функции.

Кажется, это зависит от компилятора.

Размер оператора

 sizeof unary-expression
 sizeof ( type-name )

Операндом является либо идентификатор, который является унарным выражением, либо выражение приведения типа (то есть спецификатор типа, заключенный в скобки). Унарное выражение не может представлять объект битового поля, неполный тип илиfunction designator, Результатом является беззнаковая интегральная константа. Стандартный заголовок STDDEF.H определяет этот тип как size_t,

Использовать флаг компиляции -Wall -pedantic вывести предупреждение о неверном операнде sizeof (Помните sizeof является оператором времени компиляции), Код:

$ cat sizeof.c 
#include<stdio.h> 
int main(){
    printf("%zu %p\n", sizeof(main), (void*)main);
    return 0;
} 

Сообщение компиляции с GCC версии 4.6.3 (Ubuntu/Linaro 4.6.3-1ubuntu5):

$ gcc -Wall -pedantic sizeof.c -std=c99
sizeof.c: In function ‘main’:
sizeof.c:3:30: warning: invalid application of ‘sizeof’ to a function type 
              [-pedantic]
sizeof.c:3:38: warning: ISO C forbids conversion of function pointer to 
              object pointer type [-pedantic]

Читайте также:

6.5.3.4 Размер оператора

1118 - sizeof оператор не должен применяться к выражению, имеющему тип функции или неполный тип, к названию в скобках такого типа или к выражению, которое обозначает член битового поля
1127 - Значение результата определяется реализацией, а его тип (целочисленный тип без знака) size_t, определенный в <stddef.h> (и другие заголовки)

Кроме того, правильная строка формата для size_t является %zu и если он не существует, например, компилятор Microsoft, то вы можете использовать %lu и преобразовать возвращаемое значение в unsigned long,

ISO C++ запрещает применение sizeof к выражению типа функции.

ISO / IEC 14882 на C++ гласит (раздел 5.3.3):

"Оператор размера не должен применяться к выражению, которое имеет функцию или неполный тип,..."

То же самое относится к стандарту C (ISO/IEC 9899:1999) раздел 6.5.3.4:

"Оператор sizeof не должен применяться к выражению, которое имеет тип функции или неполный тип, к названию в скобках такого типа или к выражению, которое обозначает элемент битового поля".

Согласно разделу ISO C11 6.5.3.4 The sizeof and _Alignof operators подраздел 1 (ограничения):

sizeof Оператор не должен применяться к выражению, которое имеет тип функции или неполный тип, к названию в скобках такого типа или к выражению, которое обозначает член битового поля.

Там также подраздел 4 в разделе 6.3.2.1 Lvalues, arrays, and function designators в котором говорится:

Обозначение функции - это выражение с типом функции. За исключением случаев, когда это операнд sizeof оператор, _Alignof оператор (65) или одинарный & оператор, обозначение функции с типом "тип, возвращающий функцию" преобразуется в выражение, имеющее тип "указатель на тип, возвращающий функцию".

В примечании 65 к футу, указанном оттуда, поясняется:

Поскольку это преобразование не происходит, операнд sizeof или же _Alignof оператор остается обозначением функции и нарушает ограничения в 6.5.3.4.

Согласно разделу 4 Conformance:

В этом международном стандарте "должен" должен толковаться как требование к реализации или программе; и наоборот, "не должен" должен толковаться как запрет.

Следовательно, строго соответствующая программа никогда не должна принимать размер функции. Но, опять же, он, вероятно, также должен использовать правильную форму main():-)

Однако здесь есть лазейка. Соответствующая реализация может предоставлять расширения "при условии, что они не изменяют поведение любой строго соответствующей программы" (раздел 4 Conformance подраздел 6).

Вы можете утверждать, что это изменение поведения (позволяя sizeof(function) вместо того, чтобы запретить это), но, поскольку исходная программа не была бы строго соответствующей в первую очередь, подраздел не запрещает ее.

Другие вопросы по тегам