# Unified Modeling Language
There are lots of type diagrams of the UML. One of the diagrams is Class Diagram.
## Class Diagram

Class Diagram 表示法,一個長方形,切格成三個部分,分別為
* Class name
* 一般類別 用**粗體** 表示
* 抽象類別 用*斜體* 表示
* Attributes
* Methods
* 存取資格
* "+" public
* "-" private
* "#" protected
* "~" package
## Relationship
各個Class之間會存在不同關係,關係由強到弱的排列。
* Composition 組成 (網頁與Header/body的關係)
* 我存在,你存在; 我死,你也死了。
* Aggregation 聚合(球隊與球員的關係)
*
* Assotiation 關聯(醫生與病人關係),兩種Class 可以單獨存在。
* Dependecy 依賴(圖書館與圖書的關係),某個Class改變,相對會影響到另一個Class。
* Inheritance 繼承
* Implementation 實作
### Composition(Class 之間)為組成關係
> Composition relationships when objects are composed of(or made up of) other objects.
上面意思是,對象由其他對象組成。
> Objects in a composition relationship cannot, conceptually, exist in isolation.
類別屬於這種關係的,概念上這種關係的兩種類別是不能單獨存在的。
另一種說法由生命週期來說
> 部份物件和整體物件的生命週期是一樣的。
網頁與Header/body的關係,就是這樣。

### Aggregation (Class 之間) 為聚合關係
文字定義:
> the formation of a number of things into a cluster.
UML其中一種解釋如下:
> Aggregation relationships exist when classes aggregate variables of other classes type.
>
另一種說法:
> A物件可以包含B物件,但B物件不是A物件的一部分
~~我的想法則是某個 Class 擁有 owns a 另一個的陣列~~
舉球隊與球員例子說明

從球隊來看:一個球隊可以有零到多個球員(0..*)。
從球員來看: 一個球員只可以屬於其中一個球隊,但不一定要屬於任一球隊。
程式實作如下
```
public class Team {
private String name;
private String slogan;
private String city;
private List<Player> players = new ArrayList<>();
public void addPlayer(Player player){
this.playes.add(player);
player.setTeam(this);
}
public void removePlayer(Player player){
this.players.remove(player);
player.setTeam(null);
}
}
```
```
public class player {
private String name;
private Int age;
private String homeTown;
private Team team;
}
```
### Assotiation(Class 之間)為關聯(瓜葛)關係
> Assotiation relationships often exist when classes have variables of other types, that they can invoke operations on.
當某些類別具有其他類別的變數,而且他們(某些類別)可以在其上(其他類別的變數)調用操作。
> 類別 "知道" 另一種類別
聚合與關聯的差別是我自己在研究的時候會搞不清,以下為我可以接受的解釋。
> 但是關聯關係所涉及的兩個類是處在同一層次上的,而在聚合關係中,兩個類是處在不平等層次上的,一個代表整體,另一個代表部分。
https://www.itread01.com/content/1547933415.html
**Aggregation -> 不同層級**
**Associtation -> 相同層級**
以病人與醫生的類別關係舉列

醫生與病人的關係,在架構上並沒有層級之分,所以是關聯的關係而不是聚合關係。
另外此處數字判讀為,一個醫生可以有零到多個病人。而從病人端判讀為,一個病人只能接受一個醫生進行治療。
### Dependency(Class 之間)為依賴關係
> Dependency relationships exist when classes depend on each other in such a way that a change to one class may affect the other, such as when one class accepts an instance of another class as parameter to a method.
當某個類別改變時,會影響到另一個使用到它的類別。當有某個類別的方法把另個類別的實際物件當作參數時。
舉圖書館與書的例子。

圖書館類別有一個方法會傳回一個書的類別。而改變書這個類別,相對會影響到圖書館這個類別。
Since the Library class has a method that returns a Book, changes to the Book class could result in changes to the Library class (based on how Book objects are created).
### Inheritance (Classs 之間) 為繼承關係
> It indicates that one of the two related classes (the subclass) is considered to be a specialized form of the other (the super type) and the superclass is considered a Generalization of the subclass.
父類別的架構比子類別的架構來得更廣泛,舉建築物來說,建築物最基本會有屋齡和地址,但有著不同的建築物,例如說因為在21世紀電動車較廣泛,因此現在的建築物會有充電樁這個attribute,但同時還是保有屋齡和地址的特徵。

### Implementation (Class 之間) 為實作關係
> 實作interface的所規範的方法。
以交易的例子來說,**ApplePay**這個實例需要實作付款這個規範,同樣的**信用卡**付款也需要實作付款這個界面規範。

## 畫出Class Diagram 表達以下設計
### 一個縣市類別,有多個行政區類別
#### 假設分析
假設每個縣市類別至少有一個行政區,每個行政區都屬於一個縣市。縣市和行政區似乎不能單獨,獨立存在。所以是組合Composition關係。

### 每個縣市類別只有一個市長類別,且市長只能任職於單一縣市
#### 假設分析
一開始會認為縣市與市長是聚合Aggregation的關係。很像球隊與球員的關係。但細想如果一個縣市不存在,首長也不會存在了。所以是組合關係。

### 行政區中存在多個生活圈,且生活圈可隸屬於複數個行政區
#### 假設分析
行政區與生活圈應該是有層級上的不一樣,生活圈在行政區之下。假設行政區可以擁有零到多個生活圈。生活圈至少屬於一個行政區。

### 市長類別具備三個屬性: 姓名(字串)、上任日期(日期)、個人代碼(數字),前兩個屬性為public,第三個屬性為private。

### 市長具備兩種可執行的行為: 連任,輸入日期無回傳; 領薪水,無輸入、回傳整數。

## 請設計並畫出Class Diagram 回應以下需求
### 透過API取得在當前地圖範圍內的生活圈,同時顯示在地圖與列表上
#### 分析
假設就字面上意思,不多加其他類別,例如: 生活圈Page。
就Vue.js 改變attributes,可以讓頁面重新render。

#### 優化
假設多一個物件,生活圈Page,這是一個Container,裡面有一個地圖類別實例(instance)和一個列表實例(instance)。這樣可以把生活圈Array拉高到生活圈Page。

#### 加入vuex後的優化

### 地圖可以拖曳、縮放
#### 分析

### 地圖被拖曳、縮放時,會重新呼叫API取得範圍內的生活圈
#### 分析
地圖拖曳、縮放,會改變地圖的中心點和地圖的半徑,這兩個Attributes(state),設計是只要states 一改變,就會呼叫API

### 點擊列表上的卡片時,被點選的卡片與地圖上的生活圈同步變色
#### 分析
想法是生活圈裡有一個attribute叫做isSelected,列表裡的卡片或是地圖上的區塊被點選到的時候會更新生活圈isSelected的值

### 一次只有一個卡片變色
## 請分別說明軟體設計原則SOLID,並劃出對應的Class Diagram範例
### 單一職責原則 Single Responsibility Principle
> 每個物件,不管是類別,函數,負責的功能,都應該只做一件事
>
根據這樣的描述,物件的關係應該像是Composition 組成的關係。
以網頁的Header/Body為例

### 開放封閉原則 Open-Close Principle
> 藉由增加新的程式碼來擴充系統的功能,而不是藉由修改原本已經存在的程式碼來擴充系統的功能
>
開放封閉原則可以用Class Diagram裡的繼承關係表示。不過這也代表在程式開發時,最初要設想這個物件最基本的功能。不然就是在程式開發時,做到相關物件的時候要整理歸類。這樣才能繼承後擴充功能。
以房屋為例,在沒有電動車以前,房屋這個物件是不會有充電樁。所以在開發時物件可以繼承最基本的房屋類別,再加上別的attributes

### 里氏替換原則 Liskov Substitution Peinciple
> 所有父類的功能都可以用其subclass來實現。
### 接口隔離原則 Interface Segregation Principle
> 針對不同需求的用戶,開放其對應需求的介面,提拱使用。可避免不相關的需求介面異動,造成被強迫一同面對異動的情況。
>
意思就是介面要盡量細分,不要讓類別在實踐介面時,產生不需要實踐的現象。
以房屋物件為例,假設一個建案實例裡,有一個直接連絡的功能和賞屋的功能,預售屋與中古屋、新成屋最大的不同是無屋可賞。所以介面上可以分開。

### 依賴反轉原則 Dependency Inversion Principle
> 當A模組在內部使用B模組的情況下,我們稱A為高階模組,B為低階模組。
> 高階模組不應該依賴於低階模組,**兩者都該依賴抽象介面**。
舉例假設樂居未來的地圖,可以選擇用GoogleMap或AppleMap或其他地圖呈現,那設計架構如下。

## 參考資料
[1]http://glj8989332.blogspot.com/2018/02/design-pattern-uml.html
[2]https://ithelp.ithome.com.tw/articles/10191553
[3]https://medium.com/@nwyyy/solid-%E4%B9%8B-s-%E5%96%AE%E4%B8%80%E8%81%B7%E8%B2%AC%E5%8E%9F%E5%89%87-305b9ad65e6f
[4]https://spicyboyd.blogspot.com/2018/07/umlclass-diagram-relationships.html
[結合角色]https://joeshua.pixnet.net/blog/post/36126772