The Rule of Method Design


读了Jeffrey Palermo 的随笔How to design a single method后,对他所述的方法(Method)设计的准则大部分比较赞同。方法的设计是类的设计的一部分(在面向对象设计的前提下),是比较细节的问题,但也是关乎设计是否优秀的细节。
Jeffrey Palermo 提到了下面的一些准则(斜体部分是我的理解):

1、方法的命名应清楚地表达出此方法所做的事情。

命名其实也是一门学问——看起来简单,但往往比较有经验的设计师才能作出比较合适的命名。不当的命名常常让他人误会,带来理解上的困难。一般方法的命名使用动词或者动词+名词。比如Append、Push、ShowDialog、GetName等。

2、一个方法做且只做一件事情。

有人常常一个方法中好几件事情,这是没有正确划分各个方法职责的结果。做一件比较复杂的事情,可能需要分为几个步骤来完成,我们把它拆为几个方法(一般为private的方法),每个方法完成其中一个步骤。当然,这需要根据实际情况做合适的划分。

3、一个方法要么做一些事情,要么返回一些东西。如果该方法返回一些东西的话,调用它无数次也不应当产生负面影响。

4、一个方法所占的篇幅不应超出一屏。

这是经验之谈,如果一个方法里面你写了大量的代码(比如超过50行),那该方法需要重构了。Jeffrey Palermo 甚至说一个方法最好少于10行。

5、方法的参数要少。

如果一个方法必须大量的参数,那可以将这些信息封装到一个Object中,现成的例子是.net framework中的ProcessStartInfo。个人认为一个方法的参数最好不超过5个。

6、方法仅仅依赖于方法的参数,或者由构造函数传入的类成员。

7、在合适的地方捕捉异常。

在需要对异常进行处理的地方捕捉异常,否则让其传播。

对于方法的设计准则,在不同的语言中可能会不尽相同。比如在.net中会对传入的参数做一些检查,而在native C/C++的代码中(比如wcscpy函数)总是认为调用者会保证参数正确,而根本不作任何检查,看下面代码:
wchar_t * __cdecl wcscpy(wchar_t * dst, const wchar_t * src)
{
        wchar_t 
* cp = dst;

        
while*cp++ = *src++ )
                ;               
/* Copy src over dst */

        
return( dst );
}

而在c#中:
public static string Copy(string str)
{
      
if (str == null)
      
{
            
throw new ArgumentNullException("str");
      }

      
string text1 = string.FastAllocateString(str.Length);
      
string.FillString(text1, 0, str);
      
return text1;
}


 

准则归准则,在实际开发中,还是要看具体情况。

posted @ 2006-04-20 16:42 风满袖 阅读(1817) 评论(7)  编辑 收藏 网摘 所属分类: Design

  回复  引用  查看    
#1楼 2006-04-20 19:04 | Dflying Chen      
Great Post!
  回复  引用  查看    
#2楼 2006-04-20 23:06 | kwklover      
不错, 不过:

6、方法仅仅依赖于方法的参数,或者由构造函数传入的类成员。
不解,难道方法就不会调用别的方法,调用另外的方法也是一种依赖

7、在合适的地方捕捉异常。
如果你的方法不希望调用者获得最底层的异常信息,那么应该捕捉处理,并根据需要包装后抛出新异常,不论如何,异常到了系统的顶部.都必须得到处理,而不应该抛给用户.


  回复  引用  查看    
#3楼 [楼主]2006-04-21 09:00 | 风满袖      
@kwklover

6、方法仅仅依赖于方法的参数,或者由构造函数传入的类成员。
不解,难道方法就不会调用别的方法,调用另外的方法也是一种依赖
---------------
这里的依赖不是指方法之间的依赖。即使调用了别的方法,那传给那个方法的参数也是本方法中产生的值,或者本方法的参数,或者由构造函数传入的类成员。

7、在合适的地方捕捉异常。
如果你的方法不希望调用者获得最底层的异常信息,那么应该捕捉处理,并根据需要包装后抛出新异常,不论如何,异常到了系统的顶部.都必须得到处理,而不应该抛给用户.
------------------
你说的不错。当我们需要做处理或者要添加一些值的时候,我们才捕捉异常,否则让他传播。

  回复  引用    
#4楼 2006-05-04 14:13 | It's me [未注册用户]
I dont know much about c / c# exception handling. c I think you have to implement this by yourself. c# has exception handling. But in java, exception is not really a good solution for method internal check all the time. It is definitely costly and also take out my memo from the heap. Sometimes method design should even try to avoid a hardcore exception handling ....
  回复  引用    
#5楼 2006-05-05 08:27 | billyw [未注册用户]
4、一个方法所占的篇幅不应超出一屏。

这是经验之谈,如果一个方法里面你写了大量的代码(比如超过50行),那该方法需要重构了。Jeffrey Palermo 甚至说一个方法最好少于10行。


以上的总结太夸张了!甚至偏激

  回复  引用    
#6楼 2006-05-06 11:01 | hupinfan [未注册用户]
4、一个方法所占的篇幅不应超出一屏。

这是经验之谈,如果一个方法里面你写了大量的代码(比如超过50行),那该方法需要重构了。Jeffrey Palermo 甚至说一个方法最好少于10行。

这样会造成函数的数量急剧膨胀,我不认为是个好的主意。

  回复  引用  查看    
#7楼 [楼主]2006-05-08 09:26 | 风满袖      
@hupinfan

的确,这样一来函数的数量很可能会大量增加.而函数的调用也是要花费一定的资源的.我看这都是一个度的问题.


发表评论



姓名 [登录] [注册] 
主页
Email (仅博主可见) 
验证码 *  验证码看不清,换一张
内容(请不要发表任何与政治相关的内容)  
  登录  使用高级评论   新用户注册   返回页首      

导航: 网站首页 社区 新闻 博问 闪存 网摘 招聘 .NET频道 知识库 找找看 Google站内搜索



China-pub 计算机图书网上专卖店!6.5万品种 2-8折!
China-Pub 计算机绝版图书按需印刷服务

相关文章:

相关链接: