c语言规范

来源:互联网 发布:软件项目上线确认书 编辑:程序博客网 时间:2024/04/28 16:29


1.变量定义的规范:
变量命名的一般约定为:[限定范围的前缀]+[数据类型前缀]+[有意义的单词].
[限定范围的前缀]表示该变量是全局的,静态的,类内的成员变量或局部变量。变量默认即为局部变量,固无须任何限定范围的前缀。
[数据类型前缀]表示该变量数据类型如INT,LONG等。
[有意义的单词]表示变量使用能够表示该变量真正意义的单词或单词的缩写组合表示,每个单词开头一个字母大写。
该条约定按执行的级,可分3个部分。
(1)灵活掌握的部分:
 [限定范围的前缀]与[数据类型前缀]可以灵活掌握,可要可不要。
(2)建议采用的部分:
 变量范围 限定范围的前缀
 全局的 g或g_
 静态的 s或s_
 类内的成员函数 m_
 局部变量 变量默认即为局部变量,故无须任何限定范围的前缀
 
 数据类型前缀的命名方法建议采用匈牙利命名法。
(3)必须执行的部分:
 “有意义的单词”部分必须严格执行。
  一般常用变量命名方式如下:
 》循环变量可以直接定义成i,j,k,l等单一字母变量,大小写不限制
 》计算变量:Cnt,Count,Counter等。
 》返回值变量:Ret
 》位置变量:xPos,yPos等。
 》用Width,Height,Wide等表示宽高的含义的变量
 变量定义的地方规定:
  在C语言中,在一个块中,变量必须定义在代码之前,否则编译通不过,在C++中,在一个块中,变量的定义可以和代码交替进行,即所谓的变量定义区,但必须在它所在块(BLOCK)的变量定义区,即在它的所有处理代码之前定义。
  错误的使用方法如下:
  main()
  { //块的开始,变量应该在块的开始的变量区定义
  //变量定义区
  int i=1;
  printf("print i=%d/n",i);
  //此变量应该在块(BLOCK)的开头也即在变量定义区定义
  int j=2;
  printf("print j=%d/n",j);

  上面的代码书写方式造成了块中的变量和代码混在了一起,正确的方法应该是把变量定义在变量区,把代码处理写在代码处理区,从而使块中的变量和代码分离(实际上,编译器就是这么做的)。如下为正确的使用方法。
  函数 
  {//块的开始
   
  //在块(BLOCK)的开始处定义变量
  //变量定义区
   
  int i=1;
 
  //代码处理区

  printf("print i=%d/n",i);

  for 循环
  {//块的开始

  //在块(BLOCK)的开始处定义变量
  //变量定义区:

  int j;
  ……
  //代码处理区:

  printf("print j= %d/n",j);
  ……
  }//块的结束

  }//块的结束
变量的对齐规定
变量数据类型+N个TAB+变量名+N个TAB+=+初始化值+;
其中“变量数据类型”与“变量名”之间的N个TAB中的N为直到后面变量名垂直对齐为止的值,其值必须大于1。后面的N个TAB中的N的值可等于0,但建议也使后面的初始化的值按TAB值垂直对齐,如下:
  INT nFullPicWidth =0;
  INT nFullPicHeight=0;
  LPINT lpWidthIndex =NULL;
  LPINT lpHeightIndex =NULL;
  LPDIB lpOriginDib =NULL;
  LPDIB lpScaleDib =NULL;
  RECT rcViewRect ={0,0,0,0};
  POINT posOrigin ={0,0};
  POINT AnchorPt ={0,0};
  SCALERECT rcScale; 
  int x,y;
  int X,Y;
  int i;

  另外变量的上下排列顺序遵照上宽下窄的倒三角排列方式进行排列,同时考虑到变量的长短可能相关较大,而且参数的个数可能较多的情况,这时候也可以考虑“分块,块间换行,然后块内对齐”或参照“定义的先后顺序”进行对齐。

  “{”,“}”必须对齐的规定
  “{”,“}”表示一个块(BLOCK),是一个相对完全的语义单元。其在垂直方向上必须对齐,以使得各语义块层次清楚,语义的递进关系明确。
  函数体的开头“{”,“}”的对齐规定:
  在函数的最大语义范围的一对“{”,“}”,即函数不需和函数的最左面对齐,如下所示:
  void Test()
  {
  }
而不是:
  void Test()
  |TAB |{
  |TAB |}
3.非函数块的“{”,“}”的对齐规定:
  在函数内的块,“{”如果在一行的开始处,则必须和其上一条语句在垂直方向上右递进一个TAB值,如下:
   
  if(a==b&& c==d)
  | TAB | {
  | TAB | }
4.一行语句较短时的“{”换行:
  当一条语句较短时,亦即是如下所示的情况下:
  while(1)//语句较短的情况
  | TAB | {
  | TAB | }
  但是,改为如下的换行方式时,代码看起来则紧凑,面貌一新:
  while(1){
  | TAB |……
  | TAB | }
  if(bFlag){
  | TAB | //里央有一大段代码
  | TAB |

  故一行语句较短时,不换行。
5。一行语句较长时的“{”换行。
  但是,在一行语句较长时,情形却正好相反,因为“{”被“隐藏”在一行较长的语句后面,又使得块的语义层次模糊了起来。如下:
   
  if(a==b&&c==d&&e==f…………………………){
  ……

  应该改为:
  if(a==b&&c==d&&e==f…………………………)
  | TAB| {
  | TAB| }

  故一行语句较长时,换行。一般当一行超过8个字符的位置,即回车后按TAB键后不会在上一行之后即可。
5。4快速的代码整理方法:
 在VC中利用ALT+F8可以快速的把代码整理为微软的CPP格式的。
但是微软的规范格式没有把一对大括号利用起来,例如,if语句中,微软的格式是“{”直接在if的下一行语句的对应列位置,这样读代码时,就会受这对大括号的影响。因为大括号内的内容实际是下一个层次内容,所以应该放在下一TAB列的位置。

5。5注释的规范:

 注释对于程序犹如眼睛对于人的重要性一样,没有注释的程序对于读者来说好比眼前一团漆黑,而不规范的注释和好几千度的近视眼也没有什么区别。
1。函数的注释
 函数的注释如下所示:
  ///////////////////////////////////////////////////////////// 函数名:
// HandleWriteDate(LPOVERLAPPED,LPCSTR,DWORD)
// 目的:
// 向一个COMM文件句柄(FILE HANDLE)写入一个字符串
// 参数:
//
//
// 
// 返回值
//
//
//
// 内容:
//
//
//
//
//
///////////////////////////////////////////////////
2。一行语句的注释:
  对一行语句的注释只需在其后,也即同一和最后加上“//”这一条注释”。
  如果上下有多条这样的注释,则最后用TAB上下对齐。
  对一行语句的注释如下:
  ResetSrcollInfo(g_hwndThumb); //初始化滚动条位置
  InitPicLib(g_szModoubleName); //初始化图像接口
  如果其中上下两句发球同一块之中,而且其长短相差无几,则有必要将按TAB对齐,否则直接附在其后即可。
  如果注释内容太长,也不能采用/**/注释方法而只能采用//的注释方法,当注释换行时其上下的注释应该在垂直方上向按TAB对齐。
(如果注释写在后面有种参差不齐的感觉,则也可以将注释写在所要注释的语句的上面)
 3。一块语句的注释:
  一块语句的注释类似一个函数的注释,但不同于函数注释的地方是块的注释必须TAB居中对齐,如下:
  ///////////////////////////////////////////////////////////// 
//
///////////////////////////////////////////////////////////
4。文件开头的注释:
  重要的文件需要在文件的开头加上:接口名称+功能说明+作者+日期。文件开头的注释如下:
  ///////////////////////////////////////////////////////////// 对象接口定义方法
/////////////////////////////////////////////////////////////
//
//
//
// 说明:
//
//
//
//
//
//
//
// 作者:可可熊
// 2005。6。2
///////////////////////////////////////////////////////////
5。6头文件的规范
1.防止重复编译的预编译指令:
  为了使头文件不被重复包含(这样会引起编译错误),需要加入以下预编译指令,假设头文件名为:apiclass.h,则可以加入如下预编译指令。
  #ifndef _APICALLS_H
  #define _APICALLS_H
  ……//具体申明
  #define //_APICALLS_H
2.extern 引出的变量出处的说明
  用extern引出的变量,必须说明该变量的出处。出处可以写在该变量的上面(当该变量上又有注释时)。如下所示:
  //来自Test.cpp
  estern BOOL g_bThreadExit; //线和是否嫁出的开关量


5。7建议采用的一些规则
 下面的一些规则建议采用:

1。一块语句间用最好用:“{”,“}”
每个单独的语义最好使用“{”,“}”,哪怕是一行语句,建议采用如下所示格式:

  if(a==b&&c==d&&e==f)
  | TAB |{
  Ret = FALSE;
  | TAB |}

不提倡采用:

  if(a==b&&c==d&&e==f)
  | TAB | Ret = FALSE;


2.判断条件较多时的换行对齐方式:
当判断条件较多,并且条件本身在意义上就有平等的条件和非平行的条件,如下所示:


  if(a==b&&c==d&&e!=g&&||i==d……)
  {
  ……
  }
  由于判断条件较多,且条件本身有平等的和递进的条件之分,故代码可以写成如下方式:
   

  if(a==b && c==d
  && e!=f && g!=h
  ||i==j &&k=ll
  &&m!=n&&o!p)
  | TAB | {
  | TAB | ……
  | TAB | }
 
  注意:条件与条件隔符之间最好有个空格。
3。函数调用方式的使用。

  内部使用的函数可以采用_stdcall,_cedel,static 或_stdcall,但给外部使用的函数建议采用APIENTRY,APICALL。
例如: 在CpuType.h中:
  #define APPICALL _stdcall,
4.定义变量时的变量类型的书写。

  变量的类型使用建议参照CpuType.h,即变量类型必须使用宏方式的说明,以便将来代码能移植到IA-64之上。不管是16位,32位,64位还是未来的CPU,其中CHAR,BYTE,WORD,DWORD,QWORD均是不变的,但INT类型又有:int8,int16,in32,int64等,LONG可能有long32,long64等。所以,针对不同的CPU的系统,应该使用不同的数据类型。

windows的其他类型,如LPSTR 和LPBYTE,HANDLE,LPVOID,HMDOULE,HFILE等按WINDOWS 的方式说明。

5。关于巨型函数。

  最好使函数的功能单一化,尽量避免巨型函数,但也不能走向极端写出一堆无意义的函数。


以下为需要灵活掌握的规则:
1。注释规则:
  注释可长可短,但应该是画龙点睛,简单扼要的,需要的地方必须加上,特别是在语义转折处。
2。简单函数与复杂函数的注释
  简单函数可以用一句话简单地注释在其上面,如下:
   
  //两值互换
  void Swap(int &a,int &b)

  复杂函数的注释必须严格按照上面5。5节中函数的注释执行。
3。内部函数与供别人使用的函数的注释

  内部使用的函数可以简单地注释,但供别人使用的函数必须严格注释,特别是入口参数和出口参数。

原创粉丝点击