C++代码风格规范

                                            C++代码风格规范

注释

注释对于保持代码的可读性至关重要

.h文件必须具有doxygen样式的注释:  函数变量

.cpp文件最好有注释来解释变量和算法

例如

/**
 *  A test class. .....
 */
class Test
{
  public:
    /**
     * Detailed enum description...
     */
    enum TEnum {
          TVal1 /** describe it... */ 
         } enumVar;
 
      /**
       * description of the constructor...
       */
      Javadoc_Test();
     
      /**
       * a normal member taking two arguments and returning an integer value.
       * @param a an integer argument.
       * @param s a constant character pointer.
       * @see Test()
       * @return The test results
       */
       int testMe(int a, const char *s);

空格与制表符

没有制表符,只能使用“空格”。

(您应该将编辑器设置为在按下Tab键时发出空格。)

局部变量

将函数的变量放在尽可能小的范围内,然后在声明中初始化变量。

C ++允许您在函数中的任何位置声明变量。我们建议您尽可能在局部范围内声明它们,并尽可能接近首次使用。这使读者可以更轻松地找到声明,并查看变量的类型和初始化的对象。特别是,应该使用初始化代替声明和赋值

例1
i = f(); //错误-初始化与声明分开。

int j = g(); //好-声明已初始化。

例2

vector <int> v;
v.push_back(1); //最好使用大括号初始化进行初始化。
v.push_back(2);

vector <int> v = {1,2}; //好-v开始初始化。

变量应在声明它们的地方初始化。

这样可以确保变量在任何时候都是有效的。未初始化的变量错误很难找到。

例如  

void getCenter(Ball* ball, int& x, int& y, int& z) {
    if (ball != nullprt) {
        ... ...
    }
}
 
int x, y, z;
getCenter(Ball* ball, &x, &y, &z);     // x, y, z might not be initialized

作用域较大的变量应使用长名称,作用域较小的变量可以使用短名称

Class

在类中使用声明的指定顺序:public:protected private之前:方法数据成员(变量)之前的方法,等等。

(您的类定义应从其public:部分开始,然后是protected:部分,然后是private:部分。如果这些部分中的任何一个为空,请忽略它们。)

在每个部分中,声明通常应按以下顺序进行:

使用声明,Typedef和Enums
常量(静态const数据成员)
构造函数
析构
方法,包括静态方法
数据成员(静态const数据成员除外)


功能

有意义的命名

函数名称必须反映其功能。      

应避免名称缩写。computeAverage();     //Bad:compAvg();

类成员函数(非静态)

从小写开始。例如getObject(int index);

静态功能

从大写开始。例如float CalculateMean(const Mat&a);

私人成员函数

如果愿意,可以使用_前缀来区分它。例如_getInternalObject(....);


不要在类定义中内联大方法定义:

通常,可以内联定义仅琐碎的或对性能至关重要的且非常简短的方法。有关更多详细信息,请参见内联函数。


变量命名

有意义的

名称应具有描述性;避开缩写。

// Good
int price_count_reader;
int num_errors;
int num_iterations;
// BAD
int n;                     // Meaningless.
int nerr;                  // Ambiguous abbreviation.
int n_comp_conns;          // Ambiguous abbreviation.

除布尔变量和指针外,不应使用隐式测试0

if (nLines != 0)  // NOT: if (nLines)
if (value != 0.0) // NOT: if (value)

如果有条件的话应该放在单独的行上,并且必须有{..}

好: 

if (isDone) {
    doCleanUp();
}

坏:

if (isDone) doCleanUp();
 
// VERY BAD
if (isDone)
    doCleanUp();

头文件

通常,每个  .cc .c .cpp文件都应该有一个关联的  .h 文件。

(有一些常见的例外,例如单元测试和.cc 仅包含main() 函数的小  文件  。)

正确使用头文件会对代码的可读性,大小和性能产生巨大影响。

独立的标题

1.标头应具有标头保护,应包括它需要的所有其他标头,并且不应要求定义任何特定的符号。

2.如果在.h文件中声明了模板或内联函数,请在同一文件中对其进行定义。这些构造的定义必须包含在使用它们的每个.cc文件中,否则程序可能无法在某些构造配置中链接。

3. #define Guard

所有头文件都应具有#define防护措施,以防止多次包含。符号名称的格式应为<PROJECT> _ <PATH> _ <FILE> _H_。

或使用:

#pragma once

为了保证唯一性,它们应基于项目源代码树中的完整路径。例如,项目foo中的文件foo / src / bar / baz.h应该具有以下防护:

#ifndef FOO_BAR_BAZ_H_
#define FOO_BAR_BAZ_H_
...
#endif  // FOO_BAR_BAZ_H_

包括的名称和顺序

项目的所有头文件都应列为项目源目录的后代

例如,

错误:#include“ awesome-project / src / base / logging.h”

好:#include“ base / logging.h”

使用标准顺序以提高可读性并避免隐藏的依赖项:

相关头文件,C库,C ++库,其他库的.h,项目的.h。

例如dir / foo.cc  或dir / foo_test.cc,其主要目的是实现或测试dir2 / foo2.h中的内容,请按以下步骤订购:

dir2 / foo2.h。
C系统文件。
C ++系统文件。
其他库的.h文件。
您项目的.h文件。

例如,awesome-project / src / foo / internal / fooserver.cc中的include可能看起来像这样:

#include "foo/server/fooserver.h"
#include <sys/types.h>
#include <unistd.h>
#include <hash_map>
#include <vector>
#include "base/basictypes.h"
#include "base/commandlineflags.h"
#include "foo/server/bar.h"

2.建议的格式化规则

行列

80个字符以内更好。必须少于100个字符

功能长度

1〜2页以内 <100行

参数排序

定义功能时,参数顺序为:输入,然后输出。

参考

通过引用传递的所有参数都必须标记为const。

在函数参数列表中,所有引用必须为const:

void Foo(常量字符串&in,字符串* out); 

前缀:

使用前缀可以帮助描述变量的含义 ,以防止产生误解和错误。

m→ member variable.     e.g.     mIndex.      

a → array.    e.g.   aRectangles

b → bool,     e.g.   bIsRectangleDetected

s → String.    e.g.   sName,  or   std::string   strName;

sz → Zero terminated char[] string.       e.g.   char* szName;

int pxWidth   or  int imgWidth    →   width in terms of pixels of an image with int precision

float fWidth      →  width with float precision

g→ Global variables.       gContext

k→ Constant names.       const int kDaysInAWeek = 7;

套管

类型应以大写开头。例如:typedef int Line;

变量名应以小写开头。例如 : Line line;

常量应该全部大写。例如MAX_ITERATIONS

类型名称

以大写字母开头,并且有意义

class UrlTable { ...
class UrlTableTester { ...
struct UrlTableProperties { ...
enum UrlTableErrors { ...

空白空间

使语句的各个组成部分脱颖而出。增强可读性。

a = (b + c) * d; // NOT: a=(b+c)*d
 
while (true)   // NOT: while(true)
{
  ...
 
doSomething(a, b, c, d);  // NOT: doSomething(a,b,c,d);
 
for (i = 0; i < 10; i++) {  // NOT: for(i=0;i<10;i++){
  ...

声明中的变量可以左对齐。

class A {
    AsciiFile*    file;
    int           nPoints;
    float         x, y;
};
// NOT:
class A {
    AsciiFile* file;
    int nPoints;
    float x, y;
};

3. C / C ++语言知识

应当尽量减少使用全局变量

在C ++中,根本没有理由需要使用全局变量。全局函数或文件作用域(静态)变量也是如此。

转换

使用诸如static_cast <float>(double_value)之类的C ++样式转换,或使用大括号初始化进行诸如int64 y = int64 {1} << 42之类的算术类型转换。不要使用诸如int y =(int)x或int y之类的转换格式。 = int(x)(但是在调用类类型的构造函数时可以使用后者)。

C ++引入了与C不同的转换系统,该系统区分了转换操作的类型。

C语言转换的问题在于操作的含糊不清;有时您正在执行转换(例如(int)3.5),有时您正在进行强制转换(例如(int)“ hello”)。括号初始化和C ++强制转换通常可以帮助避免这种歧义。此外,C ++强制类型转换在搜索它们时更为可见。

  • 使用括号初始化转换算术类型。这是最安全的方法,因为如果转换会导致信息丢失,则代码将无法编译。语法也很简洁。
  • 使用  static_cast 作为相当于C样式转换,当你需要明确的向上转换的指针从一类到它的父,或当你需要明确地将指针从超类的子类。在后一种情况下,必须确保您的对象实际上是子类的实例。
  • 使用const_cast 去除  const 限定符(参见  常量)。
  • 用于  reinterpret_cast 将指针类型与整数和其他指针类型进行不安全的转换。仅当您知道自己在做什么并且了解别名问题时才使用此功能。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

kevin@1024

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值