自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

面向?qū)ο笪宕笤O(shè)計原則,你學(xué)會了嗎?

開發(fā) 前端
面相對象五大設(shè)計原則SOLID,是指導(dǎo)思想,不貫徹這5大設(shè)計原則也能讓程序跑起來,但是可能就會出現(xiàn)閱讀性、維護(hù)性、正確性問題。

最近在看七牛云許式偉的架構(gòu)課, 重溫了面向?qū)ο笪宕笤O(shè)計原則(SOLID)。(當(dāng)然許老板是不可能深聊這么低級的內(nèi)容)。

注意區(qū)分設(shè)計原則和設(shè)計模式。設(shè)計原則更為抽象和泛化;設(shè)計模式也是抽象或泛化的良好實踐,但是它們提供了更具體和實用的底層建議。

面  as 向?qū)ο?大原則


Single Responsiblity Principle

單一職責(zé)原則

Open/Closed Principle

開閉原則

Likov Substitution Principle

里斯替代原則

Interface Segregation Principle

接口隔離原則

Dependency inversion

依賴倒置原則

單一職責(zé)原則

只能有一個讓組件或類發(fā)生改變的原因;或者說每個組件或類專注于單一功能,解決特定問題。

there should never be more than one reason for a class to change. A class should be focused on a single functionality, address a specific concern.

開閉原則

對擴展開放, 對修改封閉。

擴展類的幾種方式:

  • 從類繼承
  • 類中重寫同名行為
  • 擴展類的某些行為

一般我們通過繼承或者實現(xiàn)接口來實踐開閉原則。

class Person
{
public int age;
public string name;

public Person(string name, int age)
{
this.name = name;
this.age = age;
}
public virtual void SayHallo()
{
Console.WriteLine("我是{0},今年{1}", name, age);
}
}
class Student : Person
{
public string major;
public Student(string name, int age, string major) : base(name, age)
{
this.major = major;
}
public override void SayHallo() //子類中override重寫,實現(xiàn)虛方法
{
Console.WriteLine("我是{0},今年{1},正在學(xué)習(xí){2}", name, age, major);
}
}

class Program
{
static void Main(string[] args)
{
Person trevor1 = new Person("Trevor", 18);
trevor1.SayHallo();
Student trevor2 = new Student("Trevor", 18,"C#");
trevor2.SayHallo();
}
}

output:
我是Trevor,今年18
我是Trevor,今年18,正在學(xué)習(xí)C#

里氏替代原則

在父子類生態(tài)中,在父類出現(xiàn)的地方,可以用子類對象替換父類對象,同時不改變程序的功能和正確性。

。。 乍一看,這不是理所當(dāng)然嗎?

為啥單獨拎出來鞭尸,鞭策。

比如上例我們使用

Person trevor1 = new Student("trevor",18,"C#")  // 子類對象替換父類對象
trevor1.SayHello();

利用多態(tài)正確表達(dá)了含義。

但是某些情況下濫用繼承,卻不一定保證程序的正確性,會對使用者造成誤解。

比如下面經(jīng)典的[矩形-正方形求面積]反例:

public class Rectangle
{
// 分別設(shè)置寬高
public virtual double Width {get;set;}
public virtual double Height {get;set;}

public virtual void Area()
{
Console.WriteLine("面積是:" + Width * Height);
}
}

public class Square : Rectangle
{
public override double Width
{
// get;
set // 因為是正方形,想當(dāng)然重設(shè)了寬=
{
base.Width= value;
base.Height= value;
}
}

public override double Height
{
// get;
set // 因為是正方形,想當(dāng)然重設(shè)了寬=
{
base.Width = value;
base.Height = value;
}
}

public override void Area()
{
Console.WriteLine("面積是:" + Width * Width);
}
}

public class Program
{
public static void Main()
{
Rectangle s = new Rectangle();
s.Width = 2;
s.Height = 3;

s.Area();
}
}

output:
面積是:6

但是如果你[使用子類對象去替換父類對象]:

 Rectangle s2 = new Square();
s2.Width = 2;
s2.Height = 3;
s2.Area();

output:
面積是:9

Get到了嗎?我們不能想當(dāng)然的認(rèn)為子類對象就能無損替換父類對象, 根本原因是我們正方形雖然是(is a)矩形,但是我們的重寫行為破壞了父類的表達(dá),這是一種繼承的誤用。

里氏替代原則就是約束你在繼承(is a)的時候注意到這個現(xiàn)象,并提醒你規(guī)避這個問題。

這個時候,不應(yīng)該重寫父類的SetWight方法, 而應(yīng)該擴展新的方法SetLength。

接口隔離 

將胖接口修改為多個小接口,調(diào)用接口的代碼應(yīng)該比實現(xiàn)接口的代碼更依賴于接口。

why:如果一個類實現(xiàn)了胖接口的所有方法(部分方法在某次調(diào)用時并不需要),那么在該次調(diào)用時我們就會發(fā)現(xiàn)此時出現(xiàn)了(部分并不需要的方法),而并沒有機制告訴我們現(xiàn)在不應(yīng)該使用這部分方法。

how:避免胖接口,不要實現(xiàn)違反單一職責(zé)原則的接口??梢愿鶕?jù)實際多職責(zé)劃分為多接口,某個類實現(xiàn)多接口后, 在調(diào)用時以特定接口指代對象,這樣這個對象只能體現(xiàn)特定接口的方法,以此體現(xiàn)接口隔離。

 public interface IA
{
void getA();
}

interface IB
{
void getB();
}

public class Test : IA, IB
{
public string Field { get; set; }
public void getA()
{
throw new NotImplementedException();
}

public void getB()
{
throw new NotImplementedException();
}
}
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Hello World!");

IA a = new Test();
a.getA(); // 在這個調(diào)用處只能看到接口IA的方法, 接口隔離
}
}

依賴倒置原則

實現(xiàn)依賴于抽象, 抽象不依賴于細(xì)節(jié)。

Q:這個原則我其實一開始沒能理解什么叫“倒置”?

A: 但有了一點開發(fā)經(jīng)驗后開始有點心得了。

痛點:面向過程的開發(fā),上層調(diào)用下層,上層依賴于下層。當(dāng)下層變動時上層也要跟著變動,導(dǎo)致模塊復(fù)用度降低,維護(hù)成本增高。

圖片

提煉痛點:含有高層策略的模塊,如AutoSystem模塊,依賴于它所控制的低層的負(fù)責(zé)具體細(xì)節(jié)的模塊。

思路:找到一種方法使AutoSystem模塊獨立于它所控制的具體細(xì)節(jié),那么我們就可以自由地復(fù)用AutoSystem了;同時讓底層汽車廠也依賴抽象,受抽象驅(qū)動,這就形成一種“倒置”。

圖片

所以依賴倒置原則有兩個關(guān)鍵體現(xiàn):

①  高層次模塊不應(yīng)該依賴于低層實現(xiàn),而都應(yīng)該依賴于抽象;

這在上圖:AutoSystem和Car都依賴于抽象接口ICar

②  抽象不應(yīng)該依賴于具體實現(xiàn),具體實現(xiàn)應(yīng)該依賴于抽象。

第2點與第1點不是重復(fù)的,這一點意味著細(xì)節(jié)實現(xiàn)是受抽象驅(qū)動,這也是“倒置”的由來, 這一點是通過接口叫ICar而不是IAutoSystem來體現(xiàn)。

面相對象五大設(shè)計原則SOLID,是指導(dǎo)思想,不貫徹這5大設(shè)計原則也能讓程序跑起來,但是可能就會出現(xiàn)閱讀性、維護(hù)性、正確性問題。

責(zé)任編輯:武曉燕 來源: 精益碼農(nóng)
相關(guān)推薦

2024-03-05 10:09:16

restfulHTTPAPI

2024-09-09 09:00:12

架構(gòu)設(shè)計算法

2024-03-06 08:28:16

設(shè)計模式Java

2022-03-08 08:39:22

gRPC協(xié)議云原生

2024-01-01 08:15:00

應(yīng)用設(shè)計模型產(chǎn)品

2024-05-09 08:14:09

系統(tǒng)設(shè)計語言多語言

2024-01-05 07:46:15

JS克隆對象JSON

2023-04-04 08:14:45

2023-09-12 07:26:46

2023-01-10 08:43:15

定義DDD架構(gòu)

2024-02-04 00:00:00

Effect數(shù)據(jù)組件

2023-07-26 13:11:21

ChatGPT平臺工具

2024-01-19 08:25:38

死鎖Java通信

2024-01-02 12:05:26

Java并發(fā)編程

2023-08-01 12:51:18

WebGPT機器學(xué)習(xí)模型

2022-04-26 08:10:33

MySQL存儲InnoDB

2023-10-26 07:15:46

2024-05-06 00:00:00

InnoDBView隔離

2024-08-06 09:47:57

2022-07-08 09:27:48

CSSIFC模型
點贊
收藏

51CTO技術(shù)棧公眾號