По сути, причина, по которой объявлению массива внутри блока для main
нужен размер, а объявлению массива в параметре функции - нет, заключается в том, что объявление в main
является , определяющим массив, тогда как параметр функции просто получает массив, определяемый чем-то другим.
Таким образом, определение в main
нуждается в размере, поскольку оно должно зарезервировать хранилище для массива.
Параметр функции просто получает массив, поэтому ему нужно только знать, где начинается массив. Не нужно знать размер. (То есть компилятору не нужно знать размер, чтобы скомпилировать код. Функция может нуждаться в том, чтобы знать размер, чтобы выполнить свое предназначение, но это дело программиста, а не компилятора.)
Из-за правил C, массивы никогда не могут быть переданы в качестве аргументов функции. Всякий раз, когда массив задается в качестве параметра функции, компилятор автоматически преобразует его в указатель на свой первый элемент. Точно так же параметр функции может быть указателем, но не может быть массивом. Когда вы объявляете параметр функции как массив, компилятор автоматически настраивает его для объявления указателя. Поэтому объявление функции void myfoo(int array[])
автоматически настраивается на void myfoo(int *array)
.
Конкретное правило, требующее, чтобы объявление в main
имело размер: C 2018 6.7 7:
Если идентификатор объекта объявлен без привязки, тип объекта должен быть завершен к концу его декларатора или к концу его инициатора-декларатора, если у него есть инициализатор;…