Почему я могу вызвать функцию через указатель со слишком большим количеством аргументов?
Скажем, у меня есть эта функция:
int func2() {
printf("func2\n");
return 0;
}
Теперь я объявляю указатель:
int (*fp)(double);
Это должно указывать на функцию, которая принимает double
аргумент и возвращает int
,
func2
не имеет никаких аргументов, но все же, когда я пишу:
fp = func2;
fp(2);
(с 2
будучи просто произвольным числом), func2` вызывается правильно.
Это почему? Разве нет смысла в количестве параметров, которые я объявляю для указателя функции?
2 ответа
Да, в этом есть смысл. В C (но не в C++) функция, объявленная с пустым набором скобок, означает, что она принимает неопределенное количество параметров. Когда вы делаете это, вы не позволяете компилятору проверять количество и типы аргументов; это пережиток до того, как язык C был стандартизирован ANSI и ISO.
Неспособность вызвать функцию с правильным числом и типами аргументов приводит к неопределенному поведению. Если вы вместо этого явно объявите свою функцию, чтобы принять нулевые параметры, используя список параметров void
тогда компилятор выдаст вам предупреждение, когда вы назначите указатель на функцию неправильного типа:
int func1(); // declare function taking unspecified parameters
int func2(void); // declare function taking zero parameters
...
// No warning, since parameters are potentially compatible; calling will lead
// to undefined behavior
int (*fp1)(double) = func1;
...
// warning: assignment from incompatible pointer type
int (*fp2)(double) = func2;
Вам нужно явно объявить параметр, иначе вы получите неопределенное поведение:)
int func2(double x)
{
printf("func2(%lf)\n", x);
return 0;
}