代码原则一

1 基本原则
【规则1-1】首先为人编写程序,其次才是计算机。
说明:这是软件开发的基本要点,软件的生命周期贯穿产品的开发、测试、生产、用户使用、版本升级和后期维护等长期过程,只有易读、易维护的软件代码才具有生命力。
【规则1-2】保持代码的简明清晰,避免过分的技巧。
说明:简单是最美。保持代码的简单化是软件工程化的基本要求。不要过分追求技巧,否则会降低程序的可读性。
【规则1-3】所有的代码必须遵循ANSI C标准。
说明:例如函数的原型声明中,必须包含类型定义。
【规则1-4】编程时首先达到正确性,其次考虑效率。
说明:编程首先考虑的是满足正确性、健壮性、可维护性、可移植性等质量因素,最后才考虑程序的效率和资源占用。
【规则1-5】保持一致性,尽可能多的使用相同的规则。
说明:编程首先考虑的是满足正确性、健壮性、可维护性、可移植性等质量因素,最后才考虑程序的效率和资源占用。
【规则1-6】避免或少用全局变量。
说明:过多地使用全局变量,会将模块间耦合过紧,违反模块化的要求。
【规则1-7】禁止使用GOTO语句。
【规则1-8】尽可能复用、修正老的代码。
说明:选择代码完全重建不是一条最优的选择,如果可能,尽量选择可借用的代码,对其修改优化以达到自身要求。
【规则1-9】 紧凑的代码并不能保证得到高效、稳定的机器代码。

说明:防止患有“一行清”疾病,即为了把代码尽量写在源代码的一行上,使用一些稀奇古怪的表达式。“多行源代码可能产生效率高的机器代码”。
【规则1-10】决不允许同样错误出现两次。
说明:事实上,我们无法做到完全消除错误,但通过不懈的努力,可以减少同样的错误出现的次数。

2. 布局
程序布局的目的是显示出程序良好的逻辑结构,提高程序的准确性、连续性、可读性、可维护性。更重要的是,统一的程序布局和编程风格,有助于提高整个项目的开发质量,提高开发效率,降低开发成本。同时,对于普通程序员来说,养成良好的编程习惯有助于提高自己的编程水平,提高编程效率。因此,统一的、良好的程序布局和编程风格不仅仅是个人主观美学上的或是形式上的问题,而是一个涉及到产品质量,涉及到个人编程能力的提高,必须引起大家重视。
2.1 文件布局
说明:以下内容如果某些节不需要,可以忽略。但是其它节要保持该次序。
头文件布局:
文件头(参见第三章“注释”)
#ifndef 文件名_H(全大写)
#define 文件名_H
其它条件编译选项
#include(依次为标准库头文件、非标准库头文件)
常量定义
全局宏
全局数据类型
类定义
模板(template)(包括C++中的类模板和函数模板)
extern声明
全局函数原型
#endif
【规则2-1-1】 遵循统一的布局顺序来书写头文件。
【规则2-1-2】 遵循统一的布局顺序来书写实现文件。
说明:以下内容如果某些节不需要,可以忽略。但是其它节要保持该次序。
实现文件布局:
文件头(参见第三章“注释”)
#include(依次为标准库头文件、非标准库头文件)
常量定义
文件内部使用的宏
文件内部使用的数据类型
全局变量
本地变量(即静态全局变量)
局部函数原型
类的实现

全局函数
局部函数
正例:
/ ***********************************************************
* 数据类型定义 *
*********************************************************** /
typedef unsigned char BOOLEAN;
/*************************************************************
* 函数原型 *
************************************************************/
int DoSomething(void);
说明:通过宏定义来避免重复包含。
正例:
#ifndef MODULE_H
#define MODULE_H
[文件体]
#endif
正例:
#include <stdio.h>
#include “heads.h”
【规则2-1-3】 使用注释块分离上面定义的节。
【规则2-1-4】 头文件必须要避免重复包含。
【规则2-1-5】 包含标准库头文件用尖括号 < >,包含非标准库头文件用双引号 “ ”。
【规则2-1-5】遵循统一的顺序书写类的定义及实现。
说明:
类的定义(在定义文件中)按如下顺序书写:
公有属性
公有函数
保护属性
保护函数

私有函数
类的实现(在实现文件中)按如下顺序书写:
构造函数
析构函数
公有函数
保护函数
私有函数
2.2 基本格式
说明:包括空格在内不超过80个字符。
说明:这样可以防止书写失误,也易于阅读。
正例:
if (varible1 < varible2)
{
varible1 = varible2;
}
反例:下面的代码执行语句紧跟if的条件之后,而且没有加{},违反规则。
if (varible1 < varible2) varible1 = varible2;
正例:
float *pfBuffer;
反例:
float* pfBuffer;
【规则2-2-1】 程序中一行的代码和注释不能超过80个字符。
【规则2-2-2】if、for、while、do、switch、case等语句自占一行,执行语句不得紧跟其后。不论执行语句有多少都要加 { }。
【规则2-2-3】定义指针类型的数据,*应放在变量前。
〖建议2-2-1〗源程序中关系较为紧密的代码应尽可能相邻。
说明:这样便于程序阅读和查找。
正例:

iLength = 10;
iWidth = 5; // 矩形的长与宽关系较密切,放在一起。
strCaption = “Test”;
反例:
iLength = 10;
strCaption = “Test”;
iWidth = 5;
2.3 对齐
说明:消除不同编辑器对TAB处理的差异,有的代码编辑器可以设置用空格代替TAB键。
说明:这样使代码便于阅读,并且方便注释。
正例:
void Function(int iVar)
{ // 独占一行并与引用语句左对齐。
while (condition)
{
DoSomething(); // 与{ }缩进4格
}
}
反例:
void Function(int iVar){
while (condition){
DoSomething();
}}
【规则2-3-1】 禁止使用TAB键,必须使用空格进行缩进。缩进为4个空格。
【规则2-3-2】程序的分界符‘{’和‘}’应独占一行并且位于同一列,同时与引用它们的语句左对齐。{ }之内的代码块使用缩进规则对齐。
【规则2-3-3】声明类的时候,public、protected、private关键字与分界符{} 对齐,这些部分的内容要进行缩进。
说明:
正例:
class CCount
{
public: // 与 { 对齐
CCount (void); // 要进行缩进
~ CCount (void);
int GetCount(void);

void SetCount(int iCount);
private:
int m_iCount;
}
【规则2-3-4】在switch语句中,每一个case分支和default要用{ }括起来,{ }中的内容需要缩进。
说明:使程序可读性更好。
正例:
switch (iCode)
{
case 1:
{
DoSomething(); // 缩进4格
break;
}
case 2:
{ // 每一个case分支和default要用{}括起来
DoOtherThing();
break;
}
… // 其它case分支
default:
{
DoNothing();
break;
}
}
【规则2-3-5】结构型的数组、多维的数组如果在定义时初始化,按照数组的矩阵结构分行书写。
正例:
int aiNumbers[4][3] = {
1, 1, 1,
2, 4, 8,
3, 9, 27,
4, 16, 64
}

正例:
tPDBRes.wHead = 0;
tPDBRes.wTail = wMaxNumOfPDB - 1;
tPDBRes.wFree = wMaxNumOfPDB;
tPDBRes.wAddress = wPDBAddr;
tPDBRes.wSize = wPDBSize;
2.4 空行空格
说明:空行起着分隔程序段落的作用。空行得体(不过多也不过少)将使程序的布局更加清晰。
正例:
void Foo::Hey(void)
{
[Hey实现代码]
}
void Foo::Ack(void)
{
[Ack实现代码]
}
反例:
void Foo::Hey(void)
{
[Hey实现代码]
}
void Foo::Ack(void)
{
[Ack实现代码]
}
// 两个函数的实现是两个逻辑程序块,应该用空行加以分隔。
【规则2-3-6】相关的赋值语句等号对齐。
【规则2-4-1】不同逻辑程序块之间要使用空行分隔。
【规则2-4-2】一元运算符和它们的操作数之间不要使用空格。
正例:
!bValue
~iValue
++iCount
*strSource

&fSum
sizeof(fSum)
aiNumber[i] = 5;
tBox.dWidth
tBox->dWidth
正例:
fValue = fOldValue;
fTotal + fValue
iNumber += 2;
说明:const、virtual、inline、case 等关键字之后要留一个空格,否则无法辨析关键字。
if、for、while等关键字之后应留一个空格再跟左括号‘(’,以突出关键字。
说明:函数名后紧跟左括号‘(’,以与关键字区别。
正例:
例子中的 凵 代表空格。
for凵(i凵=凵0;凵i凵<凵MAX_BSC_NUM;凵i++)
{
DoSomething(iWidth,凵iHeight);
}
【规则2-4-3】多元运算符和它们的操作数之间至少需要一个空格。
【规则2-4-4】关键字之后要留空格。
【规则2-4-5】函数名之后不要留空格。
【规则2-4-6】‘(’向后紧跟,‘)’、‘,’、‘;’向前紧跟,紧跟处不留空格。‘,’之后要留空格。‘;’不是行结束符号时其后要留空格。
【规则2-4-7】注释符与注释内容之间要用一个空格进行分隔。
正例:
/* 注释内容 */
// 注释内容
反例:
/*注释内容*/
//注释内容

2.5 断行
说明:条件表达式的续行在第一个条件处对齐。
for循环语句的续行在初始化条件语句处对齐。
函数调用的续行在第一个参数处对齐。
赋值语句的续行应在赋值号处对齐。
正例:
if ((iFormat == CH_A_Format_M)
&& (iOfficeType == CH_BSC_M)) // 条件表达式的续行在第一个条件处对齐
{
DoSomething();
}
for (long_initialization_statement;
long_condiction_statement; // for循环语句续行在初始化条件语句处对齐
long_update_statement)
{
DoSomething();
}
// 函数调用的续行在第一个参数处对齐
BYTE ReportStatusCheckPara(HWND hWnd,
BYTE ucCallNo,
BYTE ucStatusReportNo);
// 赋值语句的续行应在赋值号处对齐
fTotalBill = fTotalBill + faCustomerPurchases[iID]
+ fSalesTax(faCustomerPurchases[iID]);
【规则2-5-1】长表达式(超过80个字符)要在低优先级操作符处拆分成新行,操作符放在新行之首(以便突出操作符)。拆分出的新行要进行适当的缩进,使排版整齐,语句可读。
【规则2-5-2】函数声明时,类型与名称不允许分行书写。
正例:
extern double FAR CalcArea(double dWidth, double dHeight);
反例:
extern double FAR
CalcArea(double dWidth, double dHeight);

3. 注释
注释可以分成五类:

你可能感兴趣的:(代码原则一)