1.选择专业的词
GetPage(url) 应改为 FetchPage(url) or DownloadPage(url)
BinaryTree::Size() 应改为 BinaryTree::Height() , BinaryTree::NumNodes() , or BinaryTree::MemoryBytes()
Thread::Stop() 应改为 Thread::Kill() or Thread::Pause()
2.找到更有表现力的词
send 更多选择 deliver, dispatch, announce, distribute, route
find 更多选择 search, extract, locate, recover
start 更多选择 launch, create, begin, open
make 更多选择 create, set up, build, generate, compose, add, new
3.避免像tmp和retval这样泛泛的名字
示例1:
1 retval += v[i] * v[i]; 2 3 //反面例子:除了“返回值”,没有包含更多信息 4 retval += v[i]; 5 6 //正面例子:”平方和“ 7 sum_squares += v[i]; //没有体现出”平方和“,更快地发现bug
示例2:
1 //tmp是个好名字: 作用域很小,表示临时存储 2 if (right < left) { 3 tmp = right; 4 right = left; 5 left = tmp; 6 } 7 8 //尽管作用域很小,但是重点并不在于临时存储,user_info会是一个更好的名字 9 String tmp = user.name(); 10 tmp += " " + user.phone_number(); 11 tmp += " " + user.email(); 12 ... 13 template.set("user_info", tmp); 14 15 //tmp临时存储并不准确,在后面加上后缀_file,可以更清楚地表达其含义 16 tmp_file = tempfile.NamedTemporaryFile() 17 ... 18 SaveData(tmp_file, ...)
3.循环迭代器
通常i, j, iter和it是常用的索引和循环迭代器,尽管名字空泛,但是大家都知道其含义。
但是在某些情况下会有比其更贴切的名字,例如:
//反面例子 if (clubs[i].members[k] == users[j]) //正面例子:选择club_i , members_i , users_i ) or ( ci , mi , ui ) if (clubs[ci].members[ui] == users[mi]) //Bug! 第一个字母不匹配
使用tmp,retval等空泛的名字需要好的理由,多花几秒想一个更好的名字可使自己的“命名能力”很快提升。
4.使用具体的名字代替抽象的名字
(1) 检测服务是否可以监听某个给定的TCP/IP端口 ServerCanStart() //换成更具体的名字 CanListenOnPort() (2) 禁用拷贝和赋值构造函数 DISALLOW_EVIL_CONSTRUCTORS //换成一个不那么嚣张且更具体的名字 #define DISALLOW_EVIL_CONSTRUCTORS(ClassName) ClassName(const ClassName&); void operator=(const ClassName&); //使用示例: class ClassName { private: DISALLOW_EVIL_CONSTRUCTORS(ClassName); public: ... }; (3) 命令行标志 //打印调试信息;运行速度降低,所以一般在本地使用 --run_locally //拆成两个更加明确 --extra_logging 和 --use_local_database (4) 为名字附带更多的信息 string id; // Example: "af84ef845cd8" //换为 hex_id; (5) 带单位的变量更准确 start_ms //优于start delay_secs //优于delay size_mb //优于size max_kbps //优于limit (6) 附带其他属性 plaintext_passwd //优于passwd unescaped_comment //优于comment html_utf8 //优于html data_urlenc //优于data
5.名字的长度
(1) 在小的作用域里可以使用短的名字
(2) 团队新成员能否理解名字的含义
eval 可以指代 evaluation , doc 可以指代 document , str 可以指代 string. 因此 FormatStr() 是易于理解的.
BEManager 应写为 BackEndManager. 因为很难想到BE是指代BackEnd。
6. 丢掉没用的词
ConvertToString() 应改为 ToString()
DoServeLoop() 应改为 ServeLoop()
7. 利用名字格式传递含义
类名单词首字母大写 CamelCase
变量名使用下划线 lower_separated
常量格式使用 kConstantName 而不是 CONSTANT_NAME,好处是可以和宏格式(MACRO_NAME) 区分开
使用统一的类成员变量命名规则,如 member_,在变量名后加上下划线。