本文為轉(zhuǎn)載
第一個(gè)層次:業(yè)務(wù)架構(gòu)的審查重構(gòu)
這是最高層次的代碼審查重構(gòu)每强。其實(shí)始腾,這個(gè)階段的審查并未真正涉及到具體的代碼實(shí)現(xiàn),而是針對客戶需求空执,對相應(yīng)的業(yè)務(wù)邏輯的設(shè)計(jì)進(jìn)行審查浪箭,目的在于使業(yè)務(wù)邏輯架構(gòu)的設(shè)計(jì)與用戶需求保持精確一致。這里審查所謂的業(yè)務(wù)架構(gòu)可以從兩個(gè)層次討論:首先是審查復(fù)雜且完整的業(yè)務(wù)邏輯的架構(gòu)辨绊,比如支付相關(guān)的業(yè)務(wù)邏輯架構(gòu)奶栖,導(dǎo)航,map邢羔,語音相關(guān)的業(yè)務(wù)等等驼抹。這個(gè)層次的審查需要我們充分了解相關(guān)的業(yè)務(wù)知識,進(jìn)而審查業(yè)務(wù)架構(gòu)的合理性與準(zhǔn)確性拜鹤。以支付為例框冀,我們需要熟悉支付方式以及支付的整個(gè)流程,另外還有其中涉及的一些關(guān)鍵問題敏簿。最終確保我們的業(yè)務(wù)邏輯的架構(gòu)設(shè)計(jì)符合這一系列的需求明也。
其次宣虾,審查簡單的單個(gè)功能點(diǎn)的業(yè)務(wù)邏輯設(shè)計(jì)實(shí)現(xiàn),例如用戶的注冊與登錄功能温数。我們需要確保這些業(yè)務(wù)邏輯的設(shè)計(jì)完全符合UX的設(shè)計(jì)绣硝,并最終符合用戶需求。
第二個(gè)層次:代碼架構(gòu)的審查重構(gòu)
這個(gè)層次的審查針對的是項(xiàng)目中采用的具體的架構(gòu)模式撑刺,目的在于審查代碼是否符合架構(gòu)模式鹉胖。在我們目前的項(xiàng)目中采用的是mvvm架構(gòu)模式,因此在這個(gè)層次的代碼審查的時(shí)候應(yīng)注重審查代碼是否遵循了mvvm的基本原則够傍。
View部分:其中包含了view組件以及ViewController主要的功能應(yīng)在于處理界面的顯示甫菠,而不應(yīng)有任何的業(yè)務(wù)邏輯的處理;
ViewModel部分:應(yīng)主要負(fù)責(zé)業(yè)務(wù)邏輯的處理冕屯,并不涉及任何頁面的展示邏輯寂诱。
Model部分:應(yīng)主要負(fù)責(zé)業(yè)務(wù)數(shù)據(jù)模型的建立,使用它可以根據(jù)業(yè)務(wù)邏輯建立相應(yīng)的業(yè)務(wù)數(shù)據(jù)安聘。
另外涉及到各部分之間的交互通信痰洒,項(xiàng)目中我們采用了RxSwift,因此應(yīng)遵循其相應(yīng)的語法規(guī)則與使用習(xí)慣浴韭。
最后涉及到項(xiàng)目中引入的依賴注入的框架SwInject丘喻,也要符合其使用規(guī)范,最大限度的消除依賴囱桨。
總之仓犬,在這個(gè)層次的代碼審查重構(gòu)的時(shí)候,我們應(yīng)始終把焦點(diǎn)關(guān)注在代碼是否符合我們項(xiàng)目中所采用的架構(gòu)模式舍肠。無論app開發(fā)還是web開發(fā)搀继,其實(shí)都是一個(gè)道理。
第三個(gè)層次:設(shè)計(jì)模式的審查重構(gòu)
這個(gè)階段主要針對的是面向?qū)ο箝_發(fā)中的類之間的組織結(jié)構(gòu)以及類自身行為屬性的設(shè)計(jì)翠语,這可能就會(huì)涉及到一些設(shè)計(jì)模式的使用叽躯。通過使用設(shè)計(jì)模式,可以使我們的代碼更加的可復(fù)用肌括,可擴(kuò)展以及可測試点骑。這是我們這個(gè)階段進(jìn)行設(shè)計(jì)模式的審查重構(gòu)的目的。然而設(shè)計(jì)模式的過度使用也會(huì)使代碼陷入“萬惡的深淵”谍夭,提前設(shè)計(jì)與設(shè)計(jì)過度同樣不可取黑滴。
因此設(shè)計(jì)模式的審查重構(gòu)時(shí)應(yīng)注重審查:
(1)代碼應(yīng)盡量保持簡單,只有在必要的時(shí)候才使用設(shè)計(jì)模式紧索,避免過度設(shè)計(jì)與提前設(shè)計(jì)袁辈。
(2)設(shè)計(jì)應(yīng)遵循面向?qū)ο缶幊痰腟OLID原則。
(3)使用規(guī)范化的設(shè)計(jì)模式的“術(shù)語”編寫珠漂,如設(shè)計(jì)模式中類的命名等相關(guān)“術(shù)語”應(yīng)標(biāo)準(zhǔn)化晚缩,規(guī)范化尾膊。
(4)使用結(jié)構(gòu)型設(shè)計(jì)模式進(jìn)行類的組織結(jié)構(gòu)設(shè)計(jì)。這其中包括:Composite, Decorator, Adapter, Bridge, Facade, Proxy, Flyweight荞彼。
(5)使用行為型設(shè)計(jì)模式進(jìn)行類方法的設(shè)計(jì), 進(jìn)行封裝變化冈敛,對象做為參數(shù)的封裝,對象間通信鸣皂,類間解耦合抓谴。包括:Strategy, State, Template method, Visitor, Command, Memento, Observer, Mediator, Iterator, Interpreter, Chain of responsibility。
(6)使用創(chuàng)建型設(shè)計(jì)模式進(jìn)行類型的創(chuàng)建初始化寞缝。它包括:Factory method, Abstract factory, Builder, Prototype, singleton齐邦。
第四個(gè)層次:最優(yōu)算法的審查重構(gòu)
這個(gè)層次的代碼審查重構(gòu)針對的是代碼算法的使用,主要審查面向?qū)ο箢愔蟹椒ǖ乃惴ㄔO(shè)計(jì)實(shí)現(xiàn)第租。這里說的算法的使用并非一定要使用那些經(jīng)典的算法,例如排序算法我纪,查找算法等慎宾,而指的是使用合理的數(shù)據(jù)結(jié)構(gòu)進(jìn)行時(shí)間與空間最優(yōu)化的代碼編寫,不分配不必要的空間浅悉,盡量設(shè)計(jì)時(shí)間復(fù)雜度更低的的代碼段趟据。總之术健,設(shè)計(jì)更為高效的代碼段汹碱。
第五個(gè)層次:語言與代碼規(guī)范的審查重構(gòu)
這是最后一個(gè)層次,也是最為細(xì)節(jié)性的層級:代碼的編寫荞估。在這個(gè)層次上咳促,代碼審查以及重構(gòu)時(shí)應(yīng)注重語言的最佳實(shí)踐與代碼風(fēng)格的規(guī)范。
首先勘伺,語言最佳實(shí)踐的審查與重構(gòu)跪腹。
代碼編寫首先應(yīng)符合使用的編程語言的語法規(guī)范,除此之外飞醉,我們還應(yīng)該努力踐行編程語言的最佳實(shí)踐冲茸,比如盡量使用語言已提供的庫中的API,避免重復(fù)建造輪子缅帘。我們項(xiàng)目中采用的是swift語言轴术,在涉及到集合類的遍歷處理的時(shí)候,我們不應(yīng)該自己編寫for in loop來實(shí)現(xiàn)遍歷的功能钦无,而應(yīng)使用集合類的從sequenceType中繼承而來的foreach方法逗栽,通過閉包的方式講要處理的行為變量傳人,從而實(shí)現(xiàn)遍歷處理的功能铃诬。
其次祭陷,代碼風(fēng)格的規(guī)范的審查與重構(gòu)苍凛。
統(tǒng)一的代碼風(fēng)格規(guī)范是團(tuán)隊(duì)開發(fā)的重要要素之一。代碼規(guī)范的統(tǒng)一有利于代碼的閱讀維護(hù)兵志,有利于代碼的“集體所有制”醇蝴。試想,如果團(tuán)隊(duì)中每個(gè)人都使用自己的一套代碼規(guī)范想罕,那整體的代碼風(fēng)格就可謂“百花爭放”悠栓,最后的結(jié)果就是代碼越來越混亂,且難以閱讀維護(hù)按价。我們項(xiàng)目中統(tǒng)一的代碼風(fēng)格概括來講有如下幾個(gè)方面:
(1)命名:使用帕斯卡命名法命名類名惭适,即名稱中每個(gè)單詞首字母大寫,采用形容詞+名詞的形式楼镐;駝峰法命名函數(shù)與屬性癞志,即名稱中除第一個(gè)單詞首字母小寫外,其他單詞首字母均大寫框产。函數(shù)命名采用動(dòng)詞+名詞的組合形式凄杯。屬性命名采用形容詞+名詞的形式。通過使用有意義的命名秉宿,使屬性與函數(shù)通過名稱可以自我表達(dá)戒突,從而取代注釋。
(2)函數(shù):保證每個(gè)函數(shù)的單一功能性描睦,讓每個(gè)函數(shù)只做一件事情膊存。采用“To”方法編寫函數(shù),就是將函數(shù)分步編寫忱叭,使每個(gè)步驟單獨(dú)成為一個(gè)新的函數(shù)隔崎。函數(shù)參數(shù)個(gè)數(shù)應(yīng)盡量減少,可以封裝在一起的盡量封裝起來窑多。
(3)避免重復(fù):應(yīng)避免代碼的隨處拷貝仍稀,拷貝是重復(fù)的根源之一。應(yīng)將可復(fù)用的部分提取出來埂息,供不同的使用者調(diào)用技潘。
(4)代碼一致性:一致性可以使代碼更整潔美觀。項(xiàng)目中為了保持一致性千康,我們需要一些約定俗成的事情享幽,例如命名規(guī)則,要不要使用宏定義等等拾弃。
(5)去除魔幻數(shù):不應(yīng)在代碼中硬編碼一些數(shù)據(jù)值桩,比如:expectedValue = actualValue*5 + 20,類似這種代碼豪椿,沒人能看明白代碼中的5和20是神馬意思奔坟。我們可以使用宏定義或者創(chuàng)建靜態(tài)屬性的方式實(shí)現(xiàn)携栋,定義成為可被理解閱讀的代碼。
(6)封裝條件表達(dá)式中的條件判斷:代碼中的條件表達(dá)式中如果有很多的條件判斷時(shí)咳秉,對于閱讀代碼的人來說婉支,很難讀懂到底為了判定什么東西設(shè)立的這些條件。將條件表達(dá)式中的條件判斷封裝成為一個(gè)單獨(dú)的方法澜建,并命名一個(gè)有意義的名稱向挖,可以極大的提高代碼的可讀性。
(7)函數(shù)異常處理:保持代碼的安全性炕舵,需要時(shí)刻注意異常的處理何之。異常處理分為兩個(gè)部分,首先是空值的判定咽筋,避免程序因空值造成的crash溶推。空值判定主要包括函數(shù)參數(shù)的空值判定以及內(nèi)部局部變量的空值判定奸攻;其次是異常的處理悼潭,比如io異常等等。
(8)單元測試:單元測試的重要性相信大家都應(yīng)該清楚舞箍,只是鑒于開發(fā)進(jìn)度壓力,往往被忽視皆疹。對于小型并不復(fù)雜的項(xiàng)目而言疏橄,可能單元測試的作用沒有完全體現(xiàn)出來,但是對于復(fù)雜度很高略就,團(tuán)隊(duì)規(guī)模較大的項(xiàng)目而言捎迫,單元測試就無比重要了。我目前所做的項(xiàng)目表牢,復(fù)雜度非常高窄绒,團(tuán)隊(duì)規(guī)模也很大,并且需要與歐美團(tuán)隊(duì)協(xié)同開發(fā)崔兴,因此保證單元測試的代碼覆蓋度非常重要彰导。因此,應(yīng)保證每段代碼都應(yīng)被單元測試覆蓋敲茄。
(9)多線程并發(fā)處理位谋。開發(fā)中會(huì)經(jīng)常涉及到多線程的問題,因此多線程的并發(fā)處理需要高度重視堰燎,很多問題就是由于多線程并發(fā)造成掏父。