517,六大設計原則之單一職責原則(面試點:應該有且僅有一個原因引起類的變更)

單一職責原則

應該有且僅有一個原因引起類的變更。

單一職責原則好處

  • 降低類的復雜性
    每個類實現(xiàn)單一職責液兽,并且單一職責都有清楚明確的定義奖蔓,復雜性當然降低。

  • 提高可讀性
    類的復雜性降低了千劈,當然提高了可讀性了。

  • 提高可維護性
    類的復雜性降低牌捷,可讀性好墙牌,當然好維護。

  • 提高擴展性

變更引起的風險降低暗甥,變更是必不可少的喜滨,如果接口的單一職責做的好,一個接口修改只對相應的實現(xiàn)類有影響撤防,對其它的接口沒有影響虽风,這對系統(tǒng)的擴展性,維護性都是有好處的寄月。

類的單一職責原則

一般一個對象可以分為屬性和行為二部分辜膝,所以在類的設計時,我們一般把對象的屬性抽象成一個BO(Business Object,業(yè)務對象)漾肮,把對象的行為抽象成一個Biz(Business Logic厂抖,業(yè)務邏輯)。

我們經(jīng)常會管理一個系統(tǒng)的用戶信息克懊,比如修改一個用戶的信息(id,密碼忱辅,名字),添加一個用戶信息保檐,刪除一個用戶信息耕蝉,對用戶進行處理,對用戶添加組織和角色夜只。下面有一個類圖垒在,就是實現(xiàn)此功能的:

image.png

我們假設:
如果一個用戶的屬性發(fā)生改變(id,密碼扔亥,名字),或者添加场躯,刪除用戶都會導致類的改變,也就是說此類沒有把用戶的屬性和用戶的行為分開旅挤,導致了在有用戶的屬性和用戶的行為變化時踢关,UserInfo類也會改變。這就違反了我們的單一職責原則(應該有且僅有一個原因引起類的變更)粘茄。

我們按照把用戶信息重新抽象成二個接口签舞,一個IUserBO接口負責處理用戶的屬性秕脓,一個IUserBiz接口負責處理用戶的行為,這樣用戶屬性改變儒搭,只會導致IUserBO接口改變吠架,用戶的行為改變,只會導致IUserBiz接口改變搂鲫,這樣也就更符合單一職責原則傍药。

修改后的類圖如下:

image.png

我們經(jīng)常使用的代碼示例:

IUserInfo userInfo = new UserInfo();

//userInfo當作IUserBO來使用
IUserBO userBO = (IUserBO)userInfo;
userBO.setPassword("test");

//userInfo當作IUserBiz 來使用
IUserBiz userBiz = (IUserBiz)userInfo;
userBiz.deleteUser();

在實際項目中,我們經(jīng)常使用這個符合單一職責原則的類圖:

image.png

接口的單一職責原則

先看幾個android開發(fā)中我們經(jīng)常使用的接口:

  • View的click監(jiān)聽接口OnClickListener:

在frameworks/base/core/java/android/view/View.java代碼中魂仍,接口OnClickListener定義

/**
     * Interface definition for a callback to be invoked when a view is clicked.
     */
     //View的click監(jiān)聽接口
    public interface OnClickListener {
        void onClick(View v);
    }
  • View的長按監(jiān)聽接口OnLongClickListener

在frameworks/base/core/java/android/view/View.java代碼中拐辽,接口OnLongClickListener 定義:

/**
     * Interface definition for a callback to be invoked when a view has been clicked and held.
     */
     //View的長按監(jiān)聽接口
    public interface OnLongClickListener {
        boolean onLongClick(View v);
    }
  • SeekBar控件的改變監(jiān)聽接口

  • 在frameworks/base/core/java/android/widget/SeekBar.java代碼中,接口OnSeekBarChangeListener 定義:

//SeekBar控件的改變監(jiān)聽接口
public interface OnSeekBarChangeListener {
        //進度改變監(jiān)聽
        void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser);
        //開始拖動進度條時監(jiān)聽
        void onStartTrackingTouch(SeekBar seekBar);
        //拖動進度條結束時監(jiān)聽
        void onStopTrackingTouch(SeekBar seekBar);
}

從上面的三個例子擦酌,我們可以清楚的看到OnClickListener接口只針對點擊功能定義onClick方法俱诸,OnLongClickListener接口只針對長按功能定義onLongClick方法,OnSeekBarChangeListener 接口針對SeekBar控件進度條改變功能定義了一組相關的三個方法仑氛。

可見乙埃,優(yōu)秀接口的定義都是符合單一職責原則闸英,針對單一的職責定義單一的方法或是相關的一組方法

方法的單一職責原則

其實類也好锯岖,接口也好,最后歸根到底還是要方法來支持和實現(xiàn)甫何,所以方法的單一職責是非常關鍵重要的出吹。

方法的單一職責原則簡單來說就是一個方法實現(xiàn)一個功能,解決一個方法辙喂。

符合單一職責原則的方法捶牢,會更方便系統(tǒng)的調(diào)用,但是如果方法過細的拆分巍耗,也會導致方法的劇增和類或接口的復雜秋麸,因此在具體項目中還是把握一個度。

下面一個修改用戶信息的樣例:
一個是一個方法不符合單一職責原則炬太,changerUser方法承擔多個職責灸蟆,必然導致此方法復雜,產(chǎn)適合其它方法來復用亲族。

image.png

一個是每個方法都符合單一職責原則炒考,changeUserName實現(xiàn)修改名字,changeHomeAddress實現(xiàn)修改家庭地址霎迫,changeTele實現(xiàn)修改電話斋枢,每個方法都職責明確清楚,邏輯也清晰明了知给,非常適合其它方法來調(diào)用瓤帚。

image.png

總結

對于單一職責原則,我們的建議是接口一定要做到單一職責原則,類的設計盡量做到只有一個原因引起變化戈次。

?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末轰胁,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子朝扼,更是在濱河造成了極大的恐慌赃阀,老刑警劉巖,帶你破解...
    沈念sama閱讀 211,265評論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件擎颖,死亡現(xiàn)場離奇詭異榛斯,居然都是意外死亡,警方通過查閱死者的電腦和手機搂捧,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,078評論 2 385
  • 文/潘曉璐 我一進店門驮俗,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人允跑,你說我怎么就攤上這事王凑。” “怎么了聋丝?”我有些...
    開封第一講書人閱讀 156,852評論 0 347
  • 文/不壞的土叔 我叫張陵索烹,是天一觀的道長。 經(jīng)常有香客問我弱睦,道長百姓,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,408評論 1 283
  • 正文 為了忘掉前任况木,我火速辦了婚禮垒拢,結果婚禮上,老公的妹妹穿的比我還像新娘火惊。我一直安慰自己求类,他們只是感情好,可當我...
    茶點故事閱讀 65,445評論 5 384
  • 文/花漫 我一把揭開白布屹耐。 她就那樣靜靜地躺著尸疆,像睡著了一般。 火紅的嫁衣襯著肌膚如雪张症。 梳的紋絲不亂的頭發(fā)上仓技,一...
    開封第一講書人閱讀 49,772評論 1 290
  • 那天,我揣著相機與錄音俗他,去河邊找鬼脖捻。 笑死,一個胖子當著我的面吹牛兆衅,可吹牛的內(nèi)容都是我干的地沮。 我是一名探鬼主播嗜浮,決...
    沈念sama閱讀 38,921評論 3 406
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼摩疑!你這毒婦竟也來了危融?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 37,688評論 0 266
  • 序言:老撾萬榮一對情侶失蹤雷袋,失蹤者是張志新(化名)和其女友劉穎吉殃,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體楷怒,經(jīng)...
    沈念sama閱讀 44,130評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡蛋勺,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,467評論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了鸠删。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片抱完。...
    茶點故事閱讀 38,617評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖刃泡,靈堂內(nèi)的尸體忽然破棺而出巧娱,到底是詐尸還是另有隱情,我是刑警寧澤烘贴,帶...
    沈念sama閱讀 34,276評論 4 329
  • 正文 年R本政府宣布禁添,位于F島的核電站,受9級特大地震影響庙楚,放射性物質(zhì)發(fā)生泄漏上荡。R本人自食惡果不足惜趴樱,卻給世界環(huán)境...
    茶點故事閱讀 39,882評論 3 312
  • 文/蒙蒙 一馒闷、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧叁征,春花似錦纳账、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,740評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至啤呼,卻和暖如春卧秘,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背官扣。 一陣腳步聲響...
    開封第一講書人閱讀 31,967評論 1 265
  • 我被黑心中介騙來泰國打工翅敌, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人惕蹄。 一個月前我還...
    沈念sama閱讀 46,315評論 2 360
  • 正文 我出身青樓蚯涮,卻偏偏與公主長得像治专,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子遭顶,可洞房花燭夜當晚...
    茶點故事閱讀 43,486評論 2 348

推薦閱讀更多精彩內(nèi)容