极客学院团队出品 · 更新于 2018-11-28 11:00:43

8 文档

8.1 标注代码的属性

必须在模块头部正确标注代码的属性。声明模块的所有思路来源。如果代码来源于其他代码,要注明来源及作者。

Never steal code - stealing code is taking code from some other module editing it and forgetting to say who wrote the original.

永远不要偷窃代码(从别的模块剽窃得来而又不注明原作者)。

以下是一些有用的属性范例:

-revision('Revision: 1.14 ').
-created('Date: 1995/01/01 11:21:11 ').
-created_by('eklas@erlang').
-modified('Date: 1995/01/05 13:04:07 ').
-modified_by('mbj@erlang').  

8.2 要在代码中提供关于规范的引用

在代码中提供一些指向用于理解代码的文档的交叉引用。比如,如果代码实现了一些通信协议或硬件接口,则要提供用于编写代码的文档所在的页码,或者是一份确切的引用。

8.3 记录所有错误

必须将所有的错误保存在一份独立的文档中,并记录下错误的含义和原因(参见 10.4 节内容)。

这里所说的错误是系统已经检测出来的错误。

有时,可能会在程序中用错误日志记录函数来侦测逻辑错误:

error_logger:error_msg(Format, {Descriptor, Arg1, Arg2, ....})

这时要确保将 {Descriptor, Arg1,...} 添加到错误消息文档中。

8.4 将消息中的首要数据结构记录下来

在系统不同部分间传递消息时,使用标记元组作为首要数据结构。

Erlang 的记录特性(自 Erlang 4.3 版起引入)可用于确保模块数据结构的一致性。

应该记录下数据结构的文本描述(参见 10.2 节内容)。

8.5 注释

注释应该清晰准确,避免不必要的废话,而且要保证注释与代码保持一致更新。注释可以增进对代码的理解。注释应该用文本来编写。

关于模块的注释不应有缩进,开始前应带有三个百分号字符(%%%),参见 8.10 节内容。

关于函数的注释不应带有缩进,开始前应带有 2 个百分号字符(%%),参见 8.6 节内容。

Erlang 代码中的注释应带有一个百分号字符(%)。如果一个代码行只包含一个注释,它会被认定为 Erlang 代码而进行缩进。这种注释应放置在它所针对的语句前。如果注释可以和语句放在同一行中,则优先考虑这种方式。


%% 关于函数的注释  
some_useful_functions(UsefulArgugument) ->
  another_functions(UsefulArgugument),    % 代码行尾的注释
  % 关于 complicated_stmnt 的注释,缩进级别等同  
  complicated_stmnt,
......

8.6 注释每一个函数

文档应重点记录的信息如下所示:

  • 函数的用意;
  • 函数有效输入范围。具体来说,即是函数参数的数据结构及其含义。
  • 函数输出范围。具体是指返回值所有可能的数据结构及其具体含义。
  • 如果函数实现了一个复杂的算法,则要对它进行描述。
  • 可能由exit/1, throw/1 或任何不明显的运行时错误所产生的失败和退出信号的可能原因。
  • 函数可能导出的任何副作用。

范例:


%%----------------------------------------------------------------------
%% Function: get_server_statistics/2
%% Purpose: Get various information from a process.
%% Args:   Option is normal|all.
%% Returns: A list of {Key, Value} 
%%     or {error, Reason} (if the process is dead)
%%----------------------------------------------------------------------
get_server_statistics(Option, Pid) when pid(Pid) ->
  ......  

8.7 数据结构

定义记录时,应该加入简明的文字描述。范例如下:

%% File: my_data_structures.h

%%---------------------------------------------------------------------
%% Data Type: person
%% where:
%%    name: A string (default is undefined).
%%    age: An integer (default is undefined).
%%    phone: A list of integers (default is []).
%%    dict:     A dictionary containing various information about the person. 
%%       A {Key, Value} list (default is the empty list).
%%----------------------------------------------------------------------
-record(person, {name, age, phone = [], dict = []}).  

8.8 文件头部,版权声明

每个源代码文件必须都要写明版权信息。示例如下:


%%%--------------------------------------------------------------------- 
%%% Copyright Ericsson Telecom AB 1996
%%%
%%% All rights reserved. No part of this computer programs(s) may be 
%%% used, reproduced,stored in any retrieval system, or transmitted,
%%% in any form or by any means, electronic, mechanical, photocopying,
%%% recording, or otherwise without prior written permission of 
%%% Ericsson Telecom AB.
%%%---------------------------------------------------------------------   

8.9 File headers, revision history 文件头部,修订历史

每个源代码文件都应记录下代码的修订历史,其中要清晰地标注上修改文件的人及其修改内容。


%%%--------------------------------------------------------------------- 
%%% Revision History
%%%--------------------------------------------------------------------- 
%%% Rev PA1 Date 960230 Author Fred Bloggs (ETXXXXX)
%%% Intitial pre release. Functions for adding and deleting foobars
%%% are incomplete
%%%--------------------------------------------------------------------- 
%%% Rev A Date 960230 Author Johanna Johansson (ETXYYY)
%%% Added functions for adding and deleting foobars and changed 
%%% data structures of foobars to allow for the needs of the Baz
%%% signalling system
%%%---------------------------------------------------------------------   

8.10 文件头部,描述信息

每个源代码文件头部必须带有一个关于该文件所包含模块的简单描述信息,以及所有导出函数的简要概述。


%%%--------------------------------------------------------------------- 
%%% Description module foobar_data_manipulation
%%%--------------------------------------------------------------------- 
%%% Foobars are the basic elements in the Baz signalling system. The
%%% functions below are for manipulating that data of foobars and for
%%% etc etc etc
%%%--------------------------------------------------------------------- 
%%% Exports
%%%--------------------------------------------------------------------- 
%%% create_foobar(Parent, Type)
%%%   returns a new foobar object
%%%   etc etc etc
%%%---------------------------------------------------------------------   

如果存在任何缺陷、Bug,或者重点测试的特性,则要将它们记录在一个特殊的注释里,不要隐藏这些信息。如果模块中的某些部分还未完成,则要添加一个特殊的注释。另外,为了便于将来对模块进行维护,可以把任何相关信息加以注释记录。假设已完成的产品中包含你所编写的模块,你应保证在十年内,其他人(有可能你根本不认识)仍能变更或改善它们。

8.11 对于陈旧代码,不要注释掉,直接移除它们

关于陈旧代码的用意,可以在修订历史中加入一条注释。别忘了,源代码控制系统能帮你。

8.12 使用源代码控制系统

所有非项目都必须使用源代码控制系统(如 RCS、CVS 或 Clearcase),他们能保存所有模块的更改信息。