Зачем определять прототип функции, а затем макрос препроцессора с тем же именем?

Я читаю книгу о C, и где-то в коде авторов я нашел определение прототипа функции, затем макрос с тем же именем, и нет определения самой функции ни в любом .h или .c.

Я имею в виду что-то вроде этого:

int print_my_stufff(char *stuff);
#define print_my_stuff(A) (printf("%s\n", A))
/* and print-my-stuff() function never defined anywhere else */

Код работает, но я просто не понимаю, зачем ему нужен прототип функции в первую очередь? Не мог он просто написать макрос? Какой смысл? Является ли это компилятором, что макрос должен быть оценен для выражения, которое возвращает int или что? Удаление прототипа, похоже, не изменяет поведения. Автор этого не объяснил.

Ответы

Ответ 1

Это устаревшая практика, начиная с функций inline. Если вы вызываете функцию как в print_my_stuff("hello"), тогда препроцессор увидит синтаксис вызова и вставляет содержимое макроса. Если вы используете имя иначе, как в f_ptr = &print_my_stuff, компилятор будет использовать фактическую функцию.

Вызов функции как (print_my_stuff)("hello") также обходит макрос. Некоторые параноидальные руководства по стилю даже требуют скобок определенных имен функций, потому что Macros Are Evil.