C++编程规范

上传人:夏** 文档编号:504923507 上传时间:2023-10-14 格式:DOC 页数:133 大小:433.50KB
返回 下载 相关 举报
C++编程规范_第1页
第1页 / 共133页
C++编程规范_第2页
第2页 / 共133页
C++编程规范_第3页
第3页 / 共133页
C++编程规范_第4页
第4页 / 共133页
C++编程规范_第5页
第5页 / 共133页
点击查看更多>>
资源描述

《C++编程规范》由会员分享,可在线阅读,更多相关《C++编程规范(133页珍藏版)》请在金锄头文库上搜索。

1、第0章 为什么要用C+ (11-15)0.1 原因为什么选择C+而不是C?或者更抽象一点,为什么选择面向对象语言,而不是面向过程语言或汇编语言?这是一个很好的问题。有人可能心里知道一些,但说不清楚;有人可能会想到很多,并认为这是一个很泛泛的问题,说来话长。其实答案很简单:如果是一个技术人员在问这个问题,答案是“为了(更好地)复用代码”;如果是一个非技术人员在问(比如你的老板或是什么资本家),回答只需两个字“省钱”,或者让他眼睛发亮的四个字“省很多钱”。话虽不同,其背后的道理却是一样的。软件开发己经有几十年的历史了,每个人都知道这个行业最费人力,因为从开发到测试,再到维护,基本上以人的手工为主。

2、我们还知道,软件开发人员从来都是高薪阶层。所以,软件的成本主要源于人的成本。那么如何降低成本?代码复用成了持续不断的主题。这是因为如果代码能够复用,则相应的开发时间、测试时间,以及分析修改时间都能节省下来,而这些时间都对应于软件人员的高薪。可见,代码复用率越高,成本削减的越多。C+语言,或者说所有面向对象语言,就是针对代码复用设计的。我们可以列举一下面向对象语言的有名的特点:封装:把具体实现封装在类内,而类内类外的代码只靠一些公共接口联系起来,类内实现接口的功能,类外使用接口的功能。目的是什么?类内实现变化了,可以不影响类外代码(复用);类外使用代码变化了,可以不影响类内代码(也是复用)。继承

3、:子类可以继承父类的东西(复用),也可以扩展自己新的特性,这些新特性不会影响父类,也不会影响使用父类的代码(复用),甚至子类可以直接以父类的身份,使用所有父类可使用的代码(还是复用)。多态:父类和子类可以为同一个接口(复用)提供不同的实现,外部代码不需任何改动(复用)就可以拥有不同的特性。0.2 语言的发展和代码复用 一个主流语言的出现,或者说语言发展的一次质的飞跃,其背后都有代码复用的影子。C语言取代汇编而流行,源于UNIX操作系统的开发。在这之前的操作系统,基本上是用汇编写成的,而UNIX的90%是C,只有10%左右是汇编。带来的好处是,UNIX比其他操作系统更容易移植到不同的机器上,因为

4、不必重写所有代码,90%只需重新编译(当然需要改动,现在看来改动应该还是一件艰巨的工作,但比起用汇编语言重头写要省事多了)。C+较之C在代码复用上的能力更强。一方面,C+试图不加修改地整块类复用代码,而不像C那样需要逐行扫描修改(如同UMX移植时);另一方面,C+的复用接口(主要是类接口)更丰富、灵活、安全,而C主要依靠函数接口,包容性太窄,而函数间的联系也太弱。我们再看看Java。它的流行不单是因为它也是一种面向对象的语言,还因为它在代码复用上有独到之处。我们基本上可以把一个网页看成一个程序,而浏览网页是将该程序从Internet上下载到本地机器上运行。但这个程序比较特殊,它要求能运行在所有

5、平台上(尽可能)。我们很难用C+来写这样的网页,因为C中编译器只能编译出适应一种平台(CPU)的执行代码。另一种方式是用诸如HTML之类的语言,它们的特点是将源码下载到客户端,再由客户端解释执行。我们确实希望网页一次开发,能(复)用到所有平台,但有时我们不想公开源码(这实际上是不同组织间的代码复用问题,和一个组织内部的复用还不同,因为有商业利益或版权问题)。此时,Java可以帮助我们。它实际上是设计了一个虚拟平台(CPU),所有Java语言源码都会编译成可运行在这个虚拟平台上的二进制执行程序,而客户端的Java解释器负责将这个虚拟平台的程序指令解释成真正平台的指令。可见,我们共享了目标级代码。

6、0.3 代码复用的特点从以上的分析和我们自己的开发经验可以得出代码复用的两个特点。一是代码复用是一个由简到繁、从局部到整体的不断发展的过程。由于软件本身的复杂性,我们不可能一下子把代码做到复用率极高的程度。复用的经验和手段是一个逐渐积累的过程。具体到我们自己的程序,不要指望它们一下子成为代码复用的经典,从复用一个类、一个函数,甚至一两个好的编程风格或想法入手,日积月累,你手边会逐渐形成一个复用代码库,它将是你经验和财富的宝库。如果你所在的部门已经有几个人拥有复用代码库,那么恭喜你的部门,它可以成立一个技术委员会,负责收集和整合不同的复用代码库,这标志着你的部门己具备较高的专业水准和开发较大规模

7、程序的能力。代码复用的另一个特点是:为了复用,牺牲性能、“浪费”系统资源都不在话下。我们从汇编程序、C程序、C+程序,再到Java程序可以看出,复用性越强,性能越差(成倍下降),程序尺寸越大(成倍增加),但我们还是乐此不疲。究其原因,无非是性能、系统资源可以靠突飞猛进的硬件能力弥补,而硬件的成本比起人力资源根本不值一提。由此再顺便提醒大家一句,与其沉醉于程序性能的提高,不如关注代码的可复用性。0.4 代码复用对我们的影响回到本书的话题。本书列举了几百条编码原则,其实试图说明两个问题:一是如何防范错误;一是如何更好地发挥C+语言的特点。我自认为代码复用的境界更高,超出本书的范畴,但我还希望大家能

8、思考一下,这几百条原则对代码复用有何帮助。另一方面,大家不妨回忆一下自己开发的C+代码,看看它们有多大程度的可复用性。如果不高,我们能不能问一下自己:“我有充分的理由用C+吗?效率的损失、资源的浪费都值得吗?”我们还可以考虑一下今后的项目。第1章 命名原则好的命名原则在软件开发中是很重要的,尤其在可复用代码中更是如此。好的命名应该是直观而容易理解的,在移入新环境或上下文后仍能保持这种清晰的特点,并且不易与其他组件产生名字冲突。原则1.1 关于类型名1.1.1 说明注意:缩写字当作普通字处理,即只有首字母大写。1.1.2 例子/ 类名class TnppCoverageArea_T/;/ 枚举类

9、型名enum pageCode_T/.;/ 自定义类型名typedef short Int16_T;1.1.3 原因防止与变量名冲突(变量名定义请见“原则1.2关于变量和函数名”):这种类型名定义方法和变量名会有两处不同,一是名字的第一个字母大小写不同,二是类型名以_T结尾。使得类型名更加清晰,尤其_T可以突出表示这是一个类名(T代表TYPE的意思):_T来源于POSIX的类型命名:POSIX统一采用_t命名其类名。为沿用其思想而又防止和POSIX软件包冲突(请参阅“原则1.9命名时避免使用国际组织占用的格式”)而采用_T。区分名字中各单词也可用下划线,但用大写字母会使得名字短些。缩写字当作普

10、通字处理:一是为了防止破坏该原则而造成混淆,请比较GPSReceiver_T和GpsReceiver_T谁更清楚;二是为了防止和全大写的常量名等混淆(全大写的名字请见“原则1.4关于宏、常量和模板名”)。因为namespace是表示一个逻辑组,与class或enum的某些用法类似,所以采用同样的命名原则。原则1.2 关于变量和函数名变量和函数名中首字母小写,其后每个英文单词的第一个字母大写,其他小写。(同时参阅:“原则1.7关于匿名命名空间级标识符的前缀”、“原则1.9命名时避免使用国际组织占用的格式”以及函数名的例外“原则1.3关于全大写的函数名(建议)”。)注意:缩写字当作普通字处理,即只

11、有首字母大写。12.2 例子/ 变量名int flexPageCount;/ 函数名(1ength)class String_Tpubl ic :int length(void)coust;/;/ 比较类型名和变量名GpsCommand_T gpsCommand;原则1.3关于全大写的函数名(建议)1.3.1 说明有一类函数,它们调用普通函数,只是对普通函数的错误返回做一般化处理。这些函数的名字要和所包含的函数名相同,只是全用大写字母(必要时用下划线分隔名字中的英文单词)。1.3.2例子/ 哆嗦的用法FILE*pFile=fopen (abc.txt,rw+);if(pFile=NULL)/

12、错误处理:打印错误信息等abort();ret=fseek (pFile,0,SEEK_END);if (ret !=0 )/ 错误处理:打印错误信息等abort();ret=fwrite(buffer,100,1,pFile);if ( ret100 ) / 错误处理:打印错误信息等abort();/ 简洁的用法inline FILE*F0PEN( char const* filename, char const* mode )FILE* pFile=fopen( fileName,mode );if (pFile=NULL)/错误处理:打印错误信息等abort();return pFile

13、; / 正常则返回相应的文件句柄/ FSEEK()和FWRITE()依此类推,因而上面哆嗦的代码变成FILE*pFile=FOPEN(abc.txt,rw+);FSEEK(Wile,0,SEEK_END);FWRITE(buffer,100,1,pFile);1.3.3 原因阅读简洁,读者的思路不会总是被(非主流的)错误处理代码打断。此类函数与原函数名只有大小写的区别:不会改变原函数名的意思。由于区别小,阅读时有可能误以为就是原函数,从而减少了新加的函数给阅读者造成的额外负担(注意:区别不能太小,否则录入时容易出错)。阅读时即便误以为是原函数也不会出问题,因为它们的功能完全相同,区别只是错误处

14、理方式。效率高:可用inline方式实现这类函数,相比上面“哆嗦的用法”效率一点也不损失。当在程序中要反复做错误检查时,这类函数会节省许多编程时间。原则1.4 关于宏、常量和模板名14.1 说明这些名字要全部大写;如有多个单词,用下划线分隔。宏指所有用宏形式定义的名字,包括常量类和函数类;常量也包括枚举中的常量成员。1.4.2 例子/ 常量类的宏#define PIE 3.1415926/ 函数类的宏#define MAX ( a,b ) (/*.*/)/ 常量const int LENGTH=1024;/ 枚举中的常量成员eenumBLUE,RED,WHITE;/ 模板名templetecl

15、ass TYPE_Tclass List_Tpublic :void add ( TYPE_T counst& value);/.;1.4.3原因使得此类名称更加清晰,防止与其他类型的名字(主要是变量名)冲突。函数宏之所以也用此原则是因为它在预编译时被展开(与普通函数有很大的不同),需要阅读的人意识到这一点(这是沿袭了C语言的规范)。模板用此原则是因为此种类型名非常近似于“#define”。原则1.5 关于指针编标识符名(供参考)1.5.1 说明建议以p开头或以Ptr结尾。1.5.2例子/ 指针变量名char* pName;/ 函数指针类型的名字typedef int (*CallbackFunctionPtr _T) (int parameter);1.5.3原因使阅读者不用查定义就能意识到这是一个指针:对指针的操作与其他类型变量有很大不同,比

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 建筑/环境 > 施工组织

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号