В вашем коде действительно есть проблема, но не там, где вы ожидаете:
- передача значения типа
size_t
для printf
спецификации преобразования %ld
имеет неопределенное поведение, если size_t
и unsigned long
имеют разные размеры или представления, как это имеет место во многих системах (16-разрядные системы, Windows 64-разрядные ...).
Вот исправленная версия, переносимаядля систем, не соответствующих C99, чья библиотека C printf
может не поддерживать %zu
:
#include <stdio.h>
int main(void) {
extern int a;
printf("%lu\n", (unsigned long)sizeof(a));
return 0;
}
Относительно того, почему программа компилируется и выполняется без ошибок:
- Переменная
a
объявлено внутри тела main
со связью extern
: для него не выделено места, и a
будет неопределенным вне тела main
. sizeof(a)
оцениваетсяво время компиляции в качестве константы sizeof(int)
, которая на вашей платформе равна 4
. - Компилятор не генерирует дальнейших ссылок на
a
, поэтому компоновщик не жалуется на a
нигде не определен.