| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 3651 人关注过本帖
标题:C99的变长数组意义何在?
只看楼主 加入收藏
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
收藏
得分:0 
以下是引用kenierlee在2015-8-13 09:28:11的发言:


main的返回值不是进程的退出代码吗?如果不返回整数,进程的退出代码如何设置?

跟函数的返回值一样,有需要就返回,不需要就不返回。并非任何程序都需要返回退出代码,也并非所有系统都有相同的退出码体系。除共识的零之外,同样的返回值,在不同系统有不同的意义,在系统预定的退出码区域之外的自定义返回码,对系统来说就是废的。结论:并不是一定要返回。

授人以渔,不授人以鱼。
2015-08-13 09:54
wmf2014
Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19
等 级:贵宾
威 望:216
帖 子:2039
专家分:11273
注 册:2014-12-6
收藏
得分:0 
回复 20楼 kenierlee
函数有返回值是默认行为,即使是void函数,函数调用结束后也有一个不确定的返回值的(在汇编级返回值在cpu寄存器AX(16)、EAX(32)),所以编译器强制规定main必须返回int是画蛇添足。

能编个毛线衣吗?
2015-08-13 09:55
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
收藏
得分:0 
其实学C的人,更应该懂得灵活变通。举例说,在C中,字符和整数是等价的,同样的一个整数32,使用者视之为整数,就是整数,视之为字符,就是字符,在不同编码体系的人看来,同样的字符编码,也可以代表不同的字符。同理,就是main()函数的返回码,在这个系统是这个意义,在那个系统可以有另外的意义,而对操作该系统的用户来说,如何使用退出码也是他自己的事,你的程序就算说返回1代表这个那个,他也可以自己另外赋予意义和用法,跟你约定的完全不搭边。强调必须返回点什么,其实是不必要的。int main()可以,void main()亦无不可,但最无聊的事,是有些人凡是看见void main(),就必定跳出来指责,好像不守标准就十恶不赦一样,那比制定无聊标准的人更无聊。

授人以渔,不授人以鱼。
2015-08-13 10:08
rjsp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:528
帖 子:9007
专家分:53942
注 册:2011-1-18
收藏
得分:0 
以下是引用kenierlee在2015-8-13 09:28:11的发言:

 
main的返回值不是进程的退出代码吗?如果不返回整数,进程的退出代码如何设置?

假如规定main可以不返回值,那么肯定需要另一个手段来告知调用者其有没有返回值,这就太复杂了,还不如强制规定其必须返回int或int兼容类型。
main不是一个接口函数,但main的参数和返回是接口的一部分。

VLA 之所以变成 optional,不是因为stack溢出的原因,更不是因为MS不配合的原因,而是Bjarne Stroustrup给C标准委员会的一封信。
stack溢出是没办法的(只是针对部分实现,某些实现中根本没有栈,或是从底而上的无限栈),当写个 int val; 也可能恰巧到达边缘而导致栈溢出,有两个提案……,扯太远不说了,反正已经optional了;
Bjarne Stroustrup的信中说,同志们,看VLA的使用接口,你们这是故意制造C和C++的裂痕呀(本来以为会使用类似于C++智能指针那样的手段)。
这封信的效果非常好,好到哪一步?好到两帮人愿意坐到一张桌子上(这在之前是不可想象的),并约好之后尽量互相兼容,看C++11和C11,有没有发现C++11中新增的内容(比如线程等)同时也进入了C11,真的是太阳从西边出了。
以上是 VLA 降级的真实原因,但不是官方发布的原因,官方给出的理由是:在部分平台上,VLA无法实现,或实现后不具备原本的意义。
收到的鲜花
  • pycansi2015-08-13 12:55 送鲜花  10朵   附言:你知道的太多了
2015-08-13 10:29
kenierlee
Rank: 6Rank: 6
等 级:侠之大者
威 望:3
帖 子:58
专家分:474
注 册:2015-7-28
收藏
得分:0 
以下是引用wmf2014在2015-8-13 09:55:40的发言:

函数有返回值是默认行为,即使是void函数,函数调用结束后也有一个不确定的返回值的(在汇编级返回值在cpu寄存器AX(16)、EAX(32)),所以编译器强制规定main必须返回int是画蛇添足。

ARM汇编呢?如果不显式的设置r0的值,如何返回?

[ 本帖最后由 kenierlee 于 2015-8-13 10:50 编辑 ]
2015-08-13 10:36
rjsp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:528
帖 子:9007
专家分:53942
注 册:2011-1-18
收藏
得分:0 
以下是引用wmf2014在2015-8-13 09:55:40的发言:

函数有返回值是默认行为,即使是void函数,函数调用结束后也有一个不确定的返回值的(在汇编级返回值在cpu寄存器AX(16)、EAX(32)),所以编译器强制规定main必须返回int是画蛇添足。

假如一个程序返回了0,那么怎么分辨它是 int main 返回的有意义值,还是 void main 返回的无意义值?
2015-08-13 11:15
ditg
Rank: 10Rank: 10Rank: 10
等 级:贵宾
威 望:16
帖 子:852
专家分:1937
注 册:2014-4-10
收藏
得分:0 
返回0应该是exit系统调用的事吧,linux下相当于:

movl $1, %eax
movl $0, %ebx  //返回值
int $0x80

梦想拥有一台龙芯3A-4000
2015-08-13 11:37
wmf2014
Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19
等 级:贵宾
威 望:216
帖 子:2039
专家分:11273
注 册:2014-12-6
收藏
得分:0 
回复 26楼 rjsp
我并不反对main函数return有意义的值,只是认为编译器不能把main返回int值作为标准。是否返回有意义的值应该是程序员自己决定的,而main函数类型也应该是宽泛的,不能因为没有定义成int main,编译器就不能通过编译。

能编个毛线衣吗?
2015-08-13 17:42
hjx1120
Rank: 15Rank: 15Rank: 15Rank: 15Rank: 15
来 自:李掌柜
等 级:贵宾
威 望:41
帖 子:1314
专家分:6927
注 册:2008-1-3
收藏
得分:0 
int是默认基本类型,
2015-08-13 17:51
rjsp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:528
帖 子:9007
专家分:53942
注 册:2011-1-18
收藏
得分:0 
以下是引用wmf2014在2015-8-13 17:42:40的发言:

我并不反对main函数return有意义的值,只是认为编译器不能把main返回int值作为标准。是否返回有意义的值应该是程序员自己决定的,而main函数类型也应该是宽泛的,不能因为没有定义成int main,编译器就不能通过编译。
主要在这一句“是否返回有意义的值应该是程序员自己决定的”,不是这样的,传入的参数和返回的值 是调用者和被调用者之间的约定,一个程序不能自己执行完毕就万事不顾了,它得遵守约定,除非这个程序是个操作系统,没有更上层的调用者了。

例如,我需要扫描照片,并识别出照片中的人物是谁,我的伪代码可以这么写:
调用 某扫描程序A
等待A结束,并取得A的退出码
如果 A的退出码 == 0
{
    调用 某人脸识别程序B
    等待B结束,并取得B的退出码
    如果 B的退出码 == 0
    {
        ……
    }
}
在这段代码中,A和B程序可以替换成任意一个程序,完美而通用。
但一旦有人不遵守约定,即随机给出个退出码,那么这段代码就完全废掉了,因为没法判断对方是遵守约定给了我一个正确的退出码,还是没遵守约定给我了一个随机值。就是通常所说的:一颗老鼠屎坏了一锅粥。

而你说的“不能因为没有定义成int main,编译器就不能通过编译”,我想不通为什么要定义成void main,总得有个好处吧?!(标准规定main函数中return 0;是可以省略的)
虽然C标准中对main只是简单说了一句“or in some other implementation-defined manner.”,但不言而喻的是这个 implementation-defined manner 不能破坏掉标准规定的两种main形式。
例如 char* main(void) 就不行
而 int main(int argc, char *argv[], double a, _Bool b) 就可以。
退一步,即使void main编译通过了,因为这属于implementation-defined,因此它不具有移植性,不具有和其它程序的交互能力。void比int还需要多打一个字,费这功夫,就为了使自己的代码烂掉?!
2015-08-14 09:14
快速回复:C99的变长数组意义何在?
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.019156 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved