前几天公司的大牛架构师,给我们这些新来的员工对代码和项目的规范做了一个讲座,之后总结一二,说说新的体会吧。
一、代码要求
1、好代码
好代码的要求,清新,自然,易读,易懂。
具体而言:
1)命名要规范,加注释。
类的命名:
类名采用英语名词,一般1到2个单词,如果超过,则要采用继承;
单词首字母要大写,如果2个单词,则第二个单词也大写,如 class MyClass{};
类属性命名:
开头以 "m_"开始,下划线之后跟上具体的变量类型属性,即匈牙利命名法;
2个单词以上的,第二个单词起首字母大写,如 int m_nobjCount;
静态变量的命名,以"ms_"开头;
类方法命名:
方法一般做一件事情,用动词+名词的形式表示;
方法命令采用类似驼鸟命名法,即doFile() ,首字母小写,第二个字母大写,和普通函数以作区分;
函数命名:
函数和方法一样,俄式执行一件事,为区分类的方法,采用小写形式,并加下划线,如do_data();
变量名命名:
变量名统一采用小写;
多个单词之间用下划线连接,如 char* p_tmp_buf;
静态变量 采用"s_"前置;
全局变量 采用"g_s"前置;
局部的置于for,while,switch-case 等的变量,可以适当简单,表意清楚即可,如
` for(int i=0;i<10;i++)
{
DownFile* pTmp = new DownFile();
//...
}`
方法和函数的形参命名:
采用类型的表意缩写,加上该变量名的大写单词;
多个单词的,首字母都采用大写,如
int get_down_count(int &nDownFileCount);
枚举变量和宏定义命名:
都采用 大写字母+下划线形式,如#define MAX_LEN 1024 ;
2)函数函数不要超过100行。
函数代码行数应该适当控制在100行左右,超过之后可以提炼出机制代码,另作函数;
3)缩进符不超过3个。
缩进太多,一般是嵌套的for,if,while等逻辑太多,对代码不宜理清思路,读起来费力。
**2、高内聚和低耦合**
做到高内聚和低耦合要求,需要机制和策略思想。
机制:通用性的代码。具体指
1)模块代码容易测试;
2)容易改变性:在不改变接口名的前提下,可以替换修改实现功能;
3)不容易改变性:在接口版本升级上,既要兼容老版本又要支持新版本的要求下,对接口的命名不能改变,因此只能重新实现一个新的增强版接口;
策略:是指如何在代码中提取出机制代码。
二、API设计
api设计不用c++的原因
1、c++语言本身就是数据耦合的,因为类直接暴露了c++的数据结构,从而造成数据见的耦合。
避免数据耦合可以使用 void*代替。
在.h中
“
class SocketInterface
{
public:
char m_szIp[32];
unsigned short m_sPort;
int m_nListen;
};
int init_socket(SocketInterface* handle);
int destory_socket(SocketInterface* handle);
“`
如果直接 把class申明放在.h头文件中暴露出来,用户可以随意的使用SocketInterface中的变量, 就会造成数据耦合,
在 程序中引用此库
int main()
{
SocketInterface* hdl = new SocketInterface();
strcpy(hdl->m_szIp,”127.0.0.1”);
hdl->m_sPort = 8080;
init_socket(hdl);
.accpet(hdl->m_nListen);
destory_socket(hdl);
}
此时程序还是能正常运行的,但是当 SocketInterface接口版本升级或者 某个二逼 改动了SocketInterface结构体之后,程序就可能会奔溃了。
1、改动后,我在SocketInterface中添加一个标记变量
class SocketInterface
{
public:
char m_szIp[32];
unsigned short m_sPort;
//add
int m_nIsAvalid;
int m_nListen;
};
然后在运行之前的程序的时候,程序就会挂掉。
因为,在之前程序中,加载的SocketInterface接口动态库的m_nListen变量的偏移地址已经固定了,但是由于SocketInterface接口动态库升级了,m_nListen的偏移地址已经改变了,但是改程序还是使用的之前的偏移地址,所以程序挂掉。
2、程序在SocketInterface* hdl = new SocketInterface();时为其分配的空间是 40
但是当改变之后,程序分配的空间是44,同样会造成内存泄漏。
所以这种数据耦合在项目中会很危险,应该避免。因此 使用c++不合适。
当然也是有改进方法的,
在.h文件中,
typedef void SocketHandle
int init_socket(SocketHandle** handle,char* szIp,unsigned short sPort);
int listen_socket(SocketHandle* handle,callback func);
int destory_socket(SocketHandle** handle);
在.c文件中,
class SocketInterface
{
public:
char m_szIp[32];
unsigned short m_sPort;
//add
int m_nIsAvalid;
int m_nListen;
};
int init_socket(void** handle,char* szIp,unsigned short sPort){}
int listen_socket(void* handle,callback func){}
int destory_socket(void** handle){}
这种,不把内部数据显示给用的方法,能有效避免用户随机性篡改数据造成错误。