重构学习2-消除过长参数
查看本人文章索引请通过http://www.cnblogs.com/seesea125/archive/2012/04/17/2453256.html
动机:一个方法里的参数过长,过长的参数列导致方法很难使用,因为这些参数太长难以理解,而且调用者和被调用者都必须记住这些参数的用途,另一个原因是一旦需要更多数据,就可能要增加参数或者重载这个方法。所以消除过长参数往往能提高代码的可读性。
方法:一、如果参数的值是通过调用某个函数的结果得来的,则去掉该参数,让接受该参数的函数直接调用该函数。
二、如果这些参数是来自同一实体对象,则传递这个实体对象过去即可,如果这个实体不存在,那就先创建一个。
注意:如果被调用函数使用了 [来自另一个对象的很多项数据」,这可能意味该函数实际上应该被定义在「那些数据所属的对象」中。这时候可以考虑移动方法。
示例:
比如公司OA,有一个页面显示某天某个人打卡记录是否正常,显示的格式如下:
当前日期 | 打卡人 | 上班打卡时间 | 下班打卡时间 | 是否正常上下班 | 描述 |
2012-04-17 | ZXZ | 09:10 | 18:00 | 非正常 | 迟到10分钟 |
已知的数据值有“当前日期,打卡人,上班打卡时间,下班打卡时间”,根据已知的数据判断“是否正常上下班,备注”,代码如下:
//显示考勤记录 public void ShowCheckOnWorkAttendanceRecords() { string currentDate = DateTime.Now.ToString("yyyy-MM-dd");//当前日期 string userID = "ZXZ";//打卡人 DateTime workOnTime = Convert.ToDateTime("2012-04-17 09:10:00");//上班打卡时间 DateTime workOffTime = Convert.ToDateTime("2012-04-17 18:00:00");//下班打卡时间 //判断是否正常上下班,并返回备注 string description = ""; bool isNormalWork = IsNormalWork(currentDate, userID, workOnTime, workOffTime, out description);
//显示内容调用isNormalWork 和description这两个值 } //判断是否正常上下班,并返回备注 public bool IsNormalWork(string currentDate, string userID, DateTime workOnTime, DateTime workOffTime, out string description) { //逻辑判断的方法省略...... //public bool calculate()...... description = "迟到10分钟"; return true; }
重构后的代码如下:
//首先建立一个实体存放参数里的字段以及把返回的内容也放入字段中 public class CheckOnWorkAttendanceRecords { public string CurrentDate { get; set; } public string UserID { get; set; } public DateTime WorkOnTime { get; set; } public DateTime WorkOffTime { get; set; } public bool IsNormalWork { get; set; } public string Description { get; set; } } //显示考勤记录 public void ShowCheckOnWorkAttendanceRecords() { //判断是否正常上下班,并返回备注 CheckOnWorkAttendanceRecords checkOnWorkAttendanceRecords = new CheckOnWorkAttendanceRecords(); checkOnWorkAttendanceRecords.CurrentDate = DateTime.Now.ToString("yyyy-MM-dd");//当前日期 checkOnWorkAttendanceRecords.UserID = "ZXZ";//打卡人 checkOnWorkAttendanceRecords.WorkOnTime = Convert.ToDateTime("2012-04-17 09:10:00");//上班打卡时间 checkOnWorkAttendanceRecords.WorkOffTime = Convert.ToDateTime("2012-04-17 18:00:00");//下班打卡时间 IsNormalWork(checkOnWorkAttendanceRecords); //显示内容可以直接调用checkOnWorkAttendanceRecords对象里的内容即可 } //判断是否正常上下班,并返回备注 public void IsNormalWork(CheckOnWorkAttendanceRecords checkOnWorkAttendanceRecords) { //逻辑判断的方法省略...... //public bool calculate()...... checkOnWorkAttendanceRecords.Description = "迟到10分钟"; }
重构后,代码更清晰易懂,不用在每次看IsNormalWork方法时,去查询和思考每个参数的内容,同时返回多个参数不用在OUT了,另外IsNormalWork应该属于逻辑层的逻辑,因此接下来可以把这个方法移到逻辑层相应的类中。