C++高质量编程总结-1-R (1)
1 :为了防止重复编译一些文件,应该使用结构:
#ifndef #define #endif 2 :尽量在定义变量的时候初始化,这样可以防止引用没有初始化的变量引发的错误 3 :几个推荐写法 <1>对于表达式较长的for,while等语句,可以适当的去掉一些语句,以使程序显得紧凑 推荐写法: for (i=0; i<10; i++) 不推荐写法: for (i = 0; i < 10; i++) 推荐写法: if ((a>=b) && (b>=c)) 不推荐写法: if ((a >= b) && ( b >= c )) 说明:很显然这样的程序不太好看 <2>if, while, for等关键字的后面应该跟着空格,这样突出关键字 推荐写法: for (int i=0; i<10; i++) 不推荐写法: for(int i=0; i<10; i++) <3>函数名的后面应该紧跟着括号: 推荐写法: void Fun(int a, int b) 不推荐写法: void Fun (int a, int b) ; <4>指针的推荐写法: 推荐写法: int *x = &y ; 不推荐写法: int* x = &y ; <5>一些函数如果不是很容易懂,应该在前面加上注释: 例如: /* *函数介绍: *输入参数: *输出参数: *返回值: */ void Function(float x, float y, float z) { }//end of Function 4 :注释的位置 一般放在语句的上方或者右方 5 :类中private和public的前后位置: 类中的private数据一般放在后面,因为别人不太原意看见一堆私有数据 6 :常量常用大写字母,单词之间常采用下划线来分割单词:
例如: int MAX = 100 ; int MAX_LENGTH = 100 ; 7 :变量的重要命令规则 <1> static变量 :int s_Number ; <2> member变量 :int m_Number ; <3> 如果不得已要使用全局变量,则最好在变量的名字前面加上g_表示全局变量: 例如: int g_value = 0 ; 8 :类的数据成员前面一般加上m_这样可以防止和函数的参数重名 例如: void setValue(int width, int length) { m_width = width ; m_length = length ; } 9 :布尔变量的注意点: 例如: bool flag = true ; 推荐用法: if (flag) { } if(!flag) { } 不推荐用法: if(flag == true) ; if(flat == 1); if(falg > 0) ; 不要拿着布尔变量和0和1进行比较 10:浮点数的注意点 不可以将浮点变量和任何数字进行比较,应该转换成和误差的大小进行比较: 例如: 推荐写法: if(x >= -EPSINON || x <= EPSINON) 不推荐写法: if(x == 0.0) 注意:对于整数可以直接进行比较 11:指针变量的比较: 推荐写法: if(p == NULL); if(p != NULL); 不推荐写法: if(p == 0) ; if(p != 0) ; 12:在循环语句中,for的使用频率最高,while其次,dowhile最少 13:在多重循环中,如果有可能,应该把次数多的循环放在内层,把次数比较少的循环放在外面,这样 可以提高程序的效率 14:for循环中的高效率的写法: 高效率写法: if(condition) { for(i=0; i<N; i++) doSomeThing ; } else { } 15:在switch语句中,最后即使不需要default处理,最好也要加上default处理,这样的程序比较容易: case 1: .... default: break ; 16:常量: 在C语言中,常量用#define来声明 在C++中,常量还可以用const来声明 17:const常量和define常量的比较: <1>const常量有数据类型,而define定义的常量没有数据类型,编译器可以对前者进行安全检查,对后者不能 <2>define定义的常量会产生边际效应 <3>在C++中,完全用const定义常量,不再使用define定义常量 18:在C++中,常用最好使用const来声明...const来声明常量有着比宏定义更多的优点 19:类中的const常量: 在类中,用const修饰的常量只在一个对象期间是常量,对于类来说不是常量,因为对于对象不通 这个常量的值可以不同,也就是说类中const常量的作用时间是整个对象 20:注意:类中const常量的初始化只能在初始化表中进行 例如: class Time { private: const int NO ; int hour ; int minute ; int second ; public: Time(int h, int m, int s) ; } ; Time::Time(int h, int m, int s):NO(2), hour(h), minute(m), second(s) {} 这样是错误的: Time::Time(int h, int m, int s) { hour = h ; minute = m ; second = s ; NO = 2 ; //这样是错误的!!!! } 21:如果参数要求传递的是对象不能改变对象,则函数的参数的类型应该是: const &类型的,这样传递的优点是提高传递的效率,省略构造对象的时间?????????????????????????? 22:避免函数有太多的参数,函数的参数控制在5个以内 23:隐含的错误: char c ; c = getchar() ; if(c == EOF) cout<< "End Of File" << endl << endl ; 错误: getchar()返回的整型数据,他的值的范围就是ASCII码的范围:-128,127 24:这样的隐含错误: char * fun() { char str[] = "Hello" ; return str ; } 这个函数可以说就是错误的,因为返回一个临时变量的地址 25:写return语句时的注意点 写函数return语句的时候一定要清楚返回的是值,引用,还是指针 26:如果函数的return的是一个对象,那么应该考虑效率了 例如: return String(str1+str2) ; 说明:创建一个临时变量并且返回它 ->(1)return String(str1+str2) 和 (2)String temp = str1 + str2 ; return temp 的区别: (1)编译器直接新创建一个临时对象,并且利用这个临时对象直接初始化外部的变量,效率 比较高 (2)第(2)句有几个过程,效率比较低: (1)新建一个String对象 (2)对这个对象进行初始化 (3)调用对象的拷贝函数来初始化外部的对象 27:引用和指针的比较: (1)引用不是一个变量的拷贝,也不是一个变量的指针,其实就是这个变量自己 (2)不能有NULL引用,但是可以指针可以指向NULL (3)引用一旦初始化就不能改变它的值,但是指针是可以的 28:引用和指针该如何选择呢? (1)引用可以作的事情,指针都可以做到 (2)因为指针可以指向内存中的任何空间,所以使用指针的时候一定非常小心 (3)在能用引用的地方应该就用引用,这样就可以避免危险 29:内存分配的三种方式: (1)静态内存分配: 程序中的static变量和全局变量在函数编译的时候空间就已经分配好了,这样的内存叫做 静态内存 (2)栈上分配的内存: 函数中的局部变量分配的内存是在栈上的,这些空间在函数结束的时候就会自动被分配 (3)动态内存(从堆上分配) 程序员用new和delete来分配和释放的内存,这些内存的分配比较灵活,但是问题也很多 30:断言:assert的应用: (1)程序一般分为Debug版本和Release版本,Debug版本是调试版本,是内部版本,Release版本是 发行给用户的版本 (2)assert是仅在Debug版本起作用的宏 (3)assert的作用机理: 如果assert的参数为假,那么程序就会中止 (4)assert的作用: 用于检查不该发生的情况(一般还会有提示对话,提示在什么地方发生了assert) 例如:下面的内存复制函数: void memcpy(byte *pbTo, byte *pvForm, int size) { assert((pbTo != NULL) && (pvForm != NULL)) ;//使用断言 byte * pmTo = pbTo ;//这样用于防止改变pbTo byte * pnTo = pvTo ;//同上 while(size-- > 0) *pmTo++ = *pmTo++ ; return pbTo ; } (5)断言捕捉的是非法情况,而不是错误情况 (6)在函数的入口处,检查函数参数的合法性 31:动态分配内存的注意点 一定要检查一下内存是否分配成功 32:野指针的产生: 只用free释放内存之外,但是没有给指向这个内存的指针赋值成NULL,导致这个指针变成野指针 33:在修改的时候一定要认清是常量还是变量: 例如: char *p = "Hello" ; (*p) = 'x' ; 这样是错误的,因为p指针指向的是个常量字符串,如果修改,则会产生错误! 34:字符串的内容复制和比较: (1)字符串的复制不能直接使用=来进行,比较不能直接只用==来进行 (2)复制用strcpy函数来进行,比较用strcmp函数来进行 35:申请一段空间,并进行数组间的复制: 例如: char a[] = "Hello" ; char *p = new char[strlen(a)+1] ;//分配多一个空字节的空间(字符串的性质) strcmp(p, a) ; if(strcmp(p, a) == 0); 注意:字符传的空间计算的时候一定要注意最后的哪个空字节 36:C/C++是没有办法知道一个指针指向的内存容量的,除非在申请空间的时候记住它: 例如: char * p = "Hello" ; cout<< sizeof(p) << endl ; 结果:4 4是一个指针变量所占的字节数 37:注意:数组的名字: (1)一般情况对于数组名字求sizeof,那么返回值将是数组的大小 (2)当数组名字用作函数从传递参数的时候,那么返回值将是指针的大小,因为在函数传递的时候 数组的名称实际上就是指针 |


yaya123
博客统计信息
热门文章
最新评论
友情链接