其實根本不用混淆你的代碼


酷殼中有不少有意思的文章,看起來很帶勁。本來要說大多看看則了,現在終於要學以致用了。
本人最近接手一個項目,縫縫補補幾天下來,實在有點郁悶,但是想想,自己也強不到哪里去。正如下所說:

If builders built buildings the way programmers write programs, then the first woodpecker that came along would destroy civilization.(如果建築師蓋房子就像程序員寫程序一樣,那么,第一只到來的啄木鳥就能毀掉我們的文明)

如何寫出無法維護的代碼
其實好代碼很多,開源的很多,但是往往都是代碼太多,功能太強大,而不知道從何處看起。所以,其實根本不用混淆你的代碼。
本文針對此次項目,結合以往所學所看,談談對代碼可讀性方面的認識。

程序命名


有一篇文章說史上最糟糕的兩個變量名

  • data
  • data2

僅就個人而言,並不是很反感變量名的無意義。如a1,a2,b3,b4等變量命名,如str(本人就經常使用),tmp,dt等都與data與data2所說一致,其實想想有時候使用同一種相互不約而同的命名方式有何不可,即使這是一種錯誤的命名方式。
好比看到str,我知道他是一個字符串,知道他是一個局部變量(local),而不可能是一個字段(field),對於str,我打起來很快很熟練,可能我只是在十幾行的方法中使用,這種命名有何不可。
但是還有一種人很有意思,他們不寫這種簡單的變量名,往往會這樣去聲明一個變量:

 

private DeserializeDockContent m_DeserializeDockContent;

 

或許他們實在不知道給這個字段起什么名字,但是又不能讓變量名毫無意義,所以他們一般會將整個類名寫出來,好讓人看到變量就知道他是什么類型。
相同的,他們會覺得遵守了匈牙利命名法而自豪,如果是局部變量更簡單:

 

ComponentAssembly componentAssembly = new Componentassembly("XXX");

 

文中所談使用下划線為變量名,讓我想起了一門超牛逼的編程語言:Brainfuck,很難見的只有八種運算符的語言,有興趣的可以看看。

偽裝欺詐


看到這一節的第一個程序讓我真實感覺到了牛人的創造力

 

for(j=0; j<array_len; j+=8)
{
    total += array[j+0];
    total += array[j+1];
    total += array[j+2]; /* Main body of
    total += array[j+3];  * loop is unrolled
    total += array[j+4];  * for greater speed.
    total += array[j+5];  */
    total += array[j+6];
    total += array[j+7];
}

 

至於偽裝欺詐,我想很多程序員也不至於去干如此有技術含量的事,但是不排除一些看到如下代碼的程序員會做出如何瘋狂的事情:

case "btnModify":
    mySql.Append("update mdm_attr set mdm_code='" + txtMdmCode.Text + "',mdm_name='" + txtName.Text + "',");
    mySql.Append("mdm_type='" + GetMdmType() + "',ac_num_ind='" + GetAcnumind() + "',draw_uncon_yn='" + GetDrawuncon() + "',");
    mySql.Append("qry_pwd_yn='" + GetQrypwd() + "',draw_pwd_yn='" + GetDrawpwd() + "',draw_id_yn='" + GetDrawid() + "',");
    mySql.Append("draw_seal_yn='" + GetDrawseal() + "',pwd_mach_yn='" + GetPwdmach() + "', note_type = '" + txtNotetype.Text + "',only_ind='" + GetOnlyind() + "',");
    mySql.Append(" pg_num=" + pgnum + ", pg_line=" + pgline + ",no_ind='" + GetNoind() + "',prt_ind='" + GetPrtind() + "',");
    mySql.Append(" card_type='" + GetCardType() + "',card_ind='" + GetCardInd() + "',chg_flag='" + GetChgFlag() + "',");
    mySql.Append(" fee_knd='" + GetFeeKnd() + "',min_amt=" + min_amt + ",fee_code='" +
    txtfeecode.Text.Trim() + "',");
    mySql.Append(" cif_type='" + GetCifType() + "',opn_aff_yn='" +
    GetOpnaFf() + "',");
    mySql.Append("opn_sub_cnt=" + opn_sub_cnt + ",opr_aff_yn='" + GetOpraFf() + "',");
    mySql.Append("dz_flag='" + GetDzFlag() + "',beg_date=" + beg_date + ", end_date=" + end_date + ",");
    mySql.Append(" opn_cnt=" + opn_cnt + ",sts='" + GetSts() + "',filler='" +
    txtfiller.Text.Trim() + "' ");
    mySql.Append(" where mdm_code ='" + txtMdmCode.Text.Trim().ToString() + "'");
break;

 

文檔和注釋


我一直都是一個不喜歡寫注釋的人。
在我的開發環境中將注釋的顏色盡可能的變暗,以至於我粗略一看可以忽略他。因為很多注釋真的是毫無意義。

 

xDoc.Save(savePath);
//filestream 讀取XML文件
XmlDocument _xd = new XmlDocument();
_xd.Load(savePath);
//用byte類型接收XML文件
byte[] myByte = Encoding.UTF8.GetBytes(_xd.InnerXml);
//上傳到服務器,成功后提示
if (TradeHelper.TradeUtils.SaveClientConfFile("Menu.xml", myByte, false))
{ this.ShowMessageBox("提交成功", "系統提示"); }
//獲取Menu.xml的路徑
string menuPath = Directory.GetCurrentDirectory() + "\\Menu.xml";
//讀取Menu.xml的內容
XmlDocument xd_menu = new XmlDocument();
xd_menu.Load(menuPath);
//讀取Menu_Tmp.xml 的內容
XmlDocument xd_tmp = new XmlDocument();
xd_tmp.Load(savePath);
//兩個文件內容交換(讓Menu.xml 內容替換)
xd_menu.InnerXml = xd_tmp.InnerXml;
//保存Menu.xml
xd_menu.Save(menuPath);

 

拿到一份100行的代碼,你會發現可能注釋會有50行,這將是怎么一種感覺?很多時候,我認為文檔比注釋更重要,如果公司的每個項目都有相應的一些必要文檔,我想開發人員也沒有那么累了。
可有人干過專門補注釋的事情?
由於某種原因,代碼可能要有某種形式的驗收,這時候就有個要求,注釋不能少於代碼量的1/3,好吧,我絞盡腦汁的去補注釋,有時候不得已就要使出小學應付作文字數的方式:

 

/// <summary>
/// 獲取HtmlElement 可以根據ID、Name、TagName等組合
/// ID選擇器優先級最高
/// Name選擇器如果能獲得且只有一個,直接返回,不判斷其他
/// 其他選擇器取並集 使用其他選擇器最好指定Name或TagName
/// </summary>
HtmlElement GetElement(XmlNode item)

 

其實我更想寫的是思路。

程序設計


關於XML的配置,很不幸的是我手頭有個項目基本就完全符合這種情況。而我們也確實曾經使用webservice來訪問數據庫,在數據庫中存過XML字段等等,XML很強大。
我很討厭諸如此種重構方法的方式:

更恐怖的是除了RefreshToolBox還有RefreshToolBox1、RefreshToolBox2……
雖然我也喜歡在代碼中寫Hard-coded或者說Magic Number,但是我真的很排斥用數字作為狀態碼或着說標示符去重構方法。
如果你看到如下代碼:

 

total2 = total - 45;
if(flg == 1)
{
    //...
}
if(total2 > total3)
{
    //...
}

 

還值得一說的就是過度的面向對象設計。
我至今還是不能把GOF23種設計模式說全,但是不影響我干任何事情。對設計模式的批判仿佛比設計模式的重要性還要多,而面向對象是否是一個騙局,是否符合哲學,我無法去辯駁,因為我真不怎么懂面向對象。
我只是在項目中看到,由於面向對象的設計,無故的多出了很多代碼。往往是我看到這里,跳着跳着已經忘記了初衷。
某篇文章說程序員應該克制寫代碼的沖動,而多多思考,但是正因為這種思想的影響,往往讓我很難下手。
這會讓我寫代碼越來越慢。

因為我總是會考慮很多才會下手:如何寫才能有利於擴展,如何寫代碼才會更好看,如何寫才會減少不必要的bug……以前的我是不會考慮這么多的,一旦想清楚怎么樣才能實現功能之后,我就會毫不猶豫的敲出代碼,而我現在連一個變量該如何命名都會考慮很久。其實對於這種項目來說,有些考慮確實是不必要的,程序設計的再好,再有利於擴展,也很有可能無法滿足一次需求的變動。

以上是某人的感言,很符合我現在的情況。


好了,寫了許多,就不再寫下去了。不管代碼如何,總還是要有人去維護的,每一個程序員都有把代碼寫爛的天分,看一份源碼,有時候真可以了解一個人。

我的博客原文地址:其實根本不用混淆你的代碼

歡迎來我的博客:nanqi.info


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM