在一次C语言实训中我发现老师在对无参函数的书写中写成fun2(void)的模式,这引起了我的好奇心,我只晓得fun1()和fun2(void)是两个无参函数,后者是C99中规定的,void的意思就是该函数不承受任何参数,然而我在应用的过程中除了对fun2传参会导致报错以外没有发现别的问题,所以就开始好奇为什么老师在实训时会特意在没有传参的函数里写上void。
通过谷歌搜寻失去以下论断
(C) The difference between int main() and int main(void)
A common misconception for C programmers, is to assume that a function prototyped as follows takes no arguments:
int foo();
In fact, this function is deemed to take an unknown number of arguments. Using the keyword void within the brackets is the correct way to tell the compiler that the function takes NO arguments.
参考文章:https://faq.cprogramming.com/…
然而我还是不能了解到底为什么要这样定义,最初在抖音的一个博主(抖抖代码)那里失去了解答
以下是博主演示的代码:
#include<stdio.h>
int main(void){
void fun1();
void fun2(void);
fun1();
fun2();
return 0;
}
void fun1(){
printf("doudou \n");
}
void fun2(){
printf("douodu 2\n");
}
/*
失去输入为:
doudou
douodu 2
*/
在没有传入任何参数的状况下两者都是被失常运行的。
然而如果对fun1和fun2别离进行传参,其后果如下
//fun1
#include<stdio.h>
int main(void){
void fun1();
void fun2(void);
fun1(888,999);
// fun2();
return 0;
}
void fun1(){
printf("doudou \n");
}
void fun2(){
printf("douodu 2\n");
}
//输入为
//doudou
#include<stdio.h>
int main(void){
void fun1();
void fun2(void);
// fun1(888,999);
fun2(888,999);
return 0;
}
void fun1(){
printf("doudou \n");
}
void fun2(){
printf("douodu 2\n");
}
/*输入为
test.c:20:5: error: too many arguments to function 'fun2'
fun2(888,999);
^~~~
test.c:18:10: note: declared here
void fun2(void);
*/
由此得出,在对fun1()和fun2(void)传参时,fun2会间接报错中断程序的运行。如果不含参的函数不带void并进行传参的话,外表上不会有任何影响,然而在Linux或者Unix平台中函数的参数会被推入堆栈中,所以只有读取参数所推入的寄存器便可取得传入的参数
#include <stdio.h>
int main(void)
{
void fun1();
fun1(888, 999);
return 0;
}
void fun1()
{
register int sp1 asm("di"); //关联第一个参数
register int sp2 asm("si"); //关联第二个参数
printf("%d,%d", sp1, sp2);
}
钻研这个问题破费了我三个小时,三个小时的工夫兴许能够让我学完一种个性或者几个语法糖,然而对这个小细节的求解却让我乐在其中。编程的魅力让我无法自拔。
发表回复