OOAD
Object-Oriented Analysis and Design
by Hohshen
目錄
OOA
OO World
OOA
OOA to OOP
Force
Force
DIP, OCP
依賴反轉重構三步驟
1+1~=2
OOD
SOLID
Creational
Behavioral
Structural
Architecture
basic Architecture
DDD design concept
戰略
戰術
地圖

OO World
The world is constructed of objects
- 
	identifiability可辨識性 
- 
	Attributes屬性 
- 
	Behavior行為(Operation動作操作) - 
		透過一些行為, 與其他物件發生關係(Relationship) 
 
- 
		
The world is constructed of objects
what is responsibility
What is an object?
描述著各個物件中的互動
There are too many objects (instances) and we need to classify them!
一群...
1. Relationship 和 object 相同
2. 都有著相同的Responsibility, 並朝著相同目標前進
object to class
如果有些不同=>使用abstract class
1. Explain the responsibilities of each class
2. class relationship
Class to Domain Model
What is a domain model(領域模型)
1. Structure
- 
	Class Diagram 
- 
	Object Diagram 
How to create Domain Model
UML (Unified Modeling Language)
統一塑模語言
2. Behavior
- Sequence Diagram
- State Machine Diagram(e.g. proxy)
- Activity Diagram
- Use Case Diagram
OOA
(Object-Oriented Analysis)
Phase I: Require Analysis, Create Domain Model
1. Dependency 依賴
2. Association 關聯
- Aggregation聚合
- Composition複合
3. Generalization繼承(一般化)
Relationship
如果給你一份需求,
你就能立刻看出需求中涉及的物件/類別以及之間的關係的話,
那麼這就是「架構式思維」的培養基礎
e.g. 我使用鉛筆寫字
I use pencil to write
Dependency 依賴
Human
-------
-------
+ write(pencil:Pencil)Pencil
-------
-------e.g. 老師教這個班級
Teacher teach this class
Association 關聯
Teacher
-------
-------
+ teach(class:Class):voidClass
-------
-------? teach ?
e.g. 老師教這個班級
Teacher teach this class
Association 關聯
Teacher
-------
-------
+ teach(class:Class):voidClass
-------
-------1 teach *
加上數量
- 
	how many object of teach relationshiop. focus on teach operation - 
		How many classes can a teacher teach? n-th class 
- 
		How many teachers can there be in a class? 1-th teacher 
 
- 
		
- 
	is an one-to-many association 
e.g. 學生修課, 並取得期末成績
Every student who takes this class will get a final score
Association 關聯
Student
-------
-------
+ takeClass(class:Class):voidClass
-------
-------* take *
Every student who takes this class

e.g. 學生修課, 並取得期末成績
Every student who takes this class will get a final score
Association Class關聯
Student
-------
-------
+ takeClass(class:Class):voidClass
-------
-------* take *
(relationship) will get a final
TakeClass
-------
- finalScore: int
-------1 get 1
e.g. A man is a human, and a woman is also a human
Generalization 繼承(一般化)
Woman
-------
-------
Man
-------
-------Human
-------
-------e.g. Both men and women will think.
Generalization 繼承(一般化)
Woman
-------
-------
think():voidMan
-------
-------
think():void/Human
-------
-------
+ /think():void
Abstract class (italics)
Abstract Method (italics)
箭頭
A 知道 B A--->B
AB相互 A<--->B or A---B
知道、使用的意思
來點範例吧!
Q1: secret love
0...* love 1

請表示暗戀關係
(限定人與人, 暫不考慮人獸)
Q1: secret love (1)
(many)Boy love a Girl, But girl not know.
Boy
--------
--------
+ love():voidGirl
--------
--------
+ love():void0...* crush1
Q1: secret love (2)
(many)Boy love a Girl, But girl not know.
Boy
--------
--------
+ love():voidGirl
--------
--------
+ love():void0...* crush 1
Boy
--------
--------
+ love():voidGirl
--------
--------
+ love():void0...* crush 1
Boy
--------
--------
+ love():voidGirl
--------
--------
+ love():void0...* crush 1
Person
--------
--------
+ love():void- 暗戀者
- 被暗戀者
Aggregation 聚合
Person
--------
--------
+ buy(house:House):voidHouse
--------
--------
1 Buy 0...*
擁有者獲得方塊
- 
	e.g. One person can buy many houses 
自住客
屯房客
Composition 複合
Directory
--------
--------
+ contain(file:File):voidFile
--------
--------
1 contain 0...*
Q1: Can't files be independent of directories?
Q2: When deleting a folder, will the files also be deleted?
Yes => use combination
擁有者獲得方塊
e.g. The directory on my computer contains many files
整理
Dependency
Generalization
Association
Aggregation
Composition
/RelationshipAssociationAggregationCompositionGeneralizationDependency重點在於「知識」, 不是程式實作
物件導向分析心法
這樣在程式中 work 嗎?
這樣的設計好嗎?
會不會有太多的條件式?
這邊是不是要套用什麼模式?
這邊是不是太多依賴?太過耦合?....
領域知識包含:定義、規範、邏輯、行為/流程
1. 捕捉知識點: 捕捉各個腳色
2. 建立關係
OOA to OOP
Let’s start OOA to OOP
(Object-Oriented programming)
Basic class
class Student{
	private id: number
    private age:number
    
    constructor(id:number,age:number){
    	this.id=id;
        this.setAge(age);
    }
    
    public setAge(age:number):void{
    	if(age<7||age>150){
        	throw new IllegaArgumentExecption("Age muse be with 7~150");
        }
        this.age=age;
    }
    
    public study():void{
    	console.log("Study")
    }
}class IllegalArgumentExecption extends Error{
	consturctor(message:string){
    	super(message)
    }
}getter/setter不會特別寫在Class Diagram
使用setter做Initialization verification
Student
--------
- id: int
- age: int {7<=age<=150}
--------
+study():voidOOA to OOP - Dependency
class Student{
	private id: number
    private age:number
    
    constructor(id:number,age:number){
    	//...
    }
    
    private setAge(age:number):void{
        //...
    }
    
    public study(book:Book):void{// here
    	console.log("Study" + book.getName());
    }
}Student
--------
- id: int
- age: int {7<=age<=150}
--------
+study(book:Book):voidclass Book{
	private name:string
    constructor(name:string){
    	this.name=name;
    }
    public getName(){
    	return this.name;
    }
}Book
-------
- name:string
-------Association 1 to n 單向關係
class Student{
	private id: number
    private age:number
    private subjects: Subject[]=[]
    
    constructor(id:number,age:number){
    	//...
    }
    
    private setAge(age:number):void{
        //...
    }
    
    public study(subject:Subject):void{// here
    	console.log("Study" + subject.getName());
        this.subjects.push(subject)
    }
}Student
--------
- id: int
- age: int {7<=age<=150}
--------
+study(subject:Subject):voidclass Subject{
	private name:string
    constructor(name:string){
    	this.name=name;
    }
    public getName(){
    	return this.name;
    }
}Subject
-------
- name:string
-------1 study 0...*
使用subject array代表一直有著多個Subject
Association 1 to n 雙向關係
class Student{
    private subjects: Subject[]=[]
    //...
    public study(subject:Subject):void{
    	console.log("Study" + subject.getName());
        this.subjects.push(subject)
        subject.setLearner(this)// here
    }
}Student
--------
- id: int
- age: int {7<=age<=150}
--------
+study(subject:Subject):voidclass Subject{
    private learner:Studnet
	//...
    public setLearner(lerner:Studnet){
    	this.learner=learner
    }
}Subject
-------
- name:string
-------1 study 0...*
Subject提供setLearner
Student將自己設為Subject的Learner
雖然會照成循環依賴,
但許多場合中能夠”有效地化簡程式複雜度”
比較怕的是consturctor的circular dependency
Association Class
class Student{
    private scores: Score[]=[]
    //...
    public setScore(score:Score):void{
    	this.scores.push(score)
    }
}這次並非相互持有對方,
而是雙方持有同一份註冊紀錄
Student
-------
-------
+ takeClass(class:Class):voidClass
-------
-------* take *
TakeClass
-------
- finalScore: int
-------1 get 1
class FinalScore{
	private score:number
    constructor(
    	private class:Class
        private student:Studnet,
        private score:number,
    ){
    	this.class=class;
        this.student=student;
        this.score=score;
    }
}class Class{
	private scores: Score[]=[]
	public exam(student:Student,score:number){
    	const score=new Score(this,student,score);
        student.setScore(score) //here
        this.setScore(score)	//here
    }
    public setScore(score:Score){
    	this.scores.push(score)
    }
}Aggregation/ Composition
同理 Association
Generalization
就是繼承
Force
(Find out the problem)
等等介紹的字
都來自於Design Pattern
品質的快速指引

Pattern的概念
新手:
軟體設計的快速指引
老手:
精通模式,內化了設計的本質,
將軟體從束縛中解放
Alexander從數學的觀點把大量建築案例分析,
抽象化成當使用者與建築空間互動中,
提供了253不同解決問題的模式(Pattern)
造就了四人幫GoF"設計模式"聖經
品質是"誕生"出來的,
而非被"人造"出來的
– Alexander
的永恆建築之道
e.g. 花
無論是建築物還是軟體程式,
基於pattern language 的文法,
在限定的context下,
套用patterns 來解決force和problem
孕育出生命力
從而獲得the Quality without a name
The Quality without a name
讓“特定品質”自然誕生;
這個種子就是模式語言Pattern Language
Pattern language
使用相同的文法,種出具有相同品質的結果
充滿中國風的建築
如何凸顯中國風? 建築物的元素體現了他的特色
元素: 就是它蘊含的所有模式(e.g. 燕尾脊)
以及模式與模式之間的關係
把這些關係當作一種文法,
就是所謂的Pattern Language(模式語言)
其實你無法消除這些force的存在,
只能透過建築物的型態(form)的設計
使得這些forces讓他們朝著特定方向釋放而去
如果沒有妥善處理,就會照成彼此衝突, 
失去生命力
Force 力(抑鬱的壓力)
從一次次的force中,
順應著force,發展出各式各樣的模式,
打造出各式建築
Pattern
1. 在Context下找到Problem.
2. 這個Problem下遇到了什麼Force,
以造成此Problem.
3. 將每個Force提出解決方案Solution
4. 最後得到了Resulting Context
流程
a pattern is a solution to a problem in a context
每個模式都次在每個情境下,針對一個問題提出的解決方案
context: 你目前關心的項目(情境)
e.g. context: 肥宅工程師 problem: 如何變瘦? force: 1. 重訓好無聊 2. 效果慢,容易放棄 solution: 改上拳擊課 resulting context: 不但變瘦,還學習到了拳擊技巧
=>肥宅變瘦模式
Form
不過我們無法透過文字來描述這些solution,
所以必須繪製出這些solution的形狀 — form 以表達這個模式
所以我們會使用form來代稱solution,
最常來表達form的就是使用uml
One pattern at a time
重構三步驟
遇到Problem=> 尋找pattern,找到對應的pattern
基於pattern的語法, 藉由[重構三步驟]來重構
1. Encapsulation what varies 封裝變動處
2. Abstract common behaviors 萃取共同行為
3. Delegation/Composition 委派或複合
這三個步驟,幫你形塑出了該pattern的form,
化解了所有forces
重構三步驟
「萃取」 (Abstract)
Person
-------
-------OOA
/Car
-------
+ 載(person:Person):void
+ /發動引擎():void
-------/Motorcycle
-------
+ 載(person:Person):void
+ /發動引擎():void
-------電動車
-------
+ 發動引擎():void
-------油車
-------
+ 發動引擎():void
-------普通機車
-------
+ 發動引擎():void
-------「萃取」 (Abstract)
Person
-------
-------OOD
電動車
-------
-------
+ 發動引擎():void油車
-------
-------
+ 發動引擎():void
普通機車
-------
-------
+ 發動引擎():void
<<interface>> 交通工具
-----
-----
+ 發動引擎():void
+ 載(person:Person):void
/Motorcycle
-------
-------
+ 載(person:Person):void
+ /發動引擎():void/Car
-------
-------
+ 載(person:Person):void
+ /發動引擎():void來個範例吧!
Problem: 如何讓英雄有不同的行為組合,不造成繼承上的組合爆炸
public void attack(hero:Hero){
	switch(attackType){
    	case "NormalAttack":
        	hero.damage(10)
        case "MagicAttack": 
        	hero.damage(20)
        case "UltimateAttack":
        	hero.damage(30)
    }
}Force: 
1. 行為變動性
2. 維護性
3. 擴充性
1. Encapsulation what varies 封裝變動處
public void attack(hero:Hero){
	switch(attackType){
    	case "NormalAttack":
        	hero.damage(10)
        case "MagicAttack": 
        	hero.damage(20)
        case "UltimateAttack":
        	hero.damage(30)
    }
}class NormalAttack
	+ attack(attacker:Hero, attacked:Hero):void
}
class MagicAttack
	+ attack(attacker:Hero, attacked:Hero):void
}
class UltimateAttack
	+ attack(attacker:Hero, attacked:Hero):void
}決定屬性(Attribute)和行為(Behavior)的可視範圍(Visibility)
=>透過封裝隱藏了一些屬性和行為
針對每個行為變種,創建一個類別來去封裝他
2. Abstract common behaviors 萃取共同行為
class UltimateAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}查看這些class的共同處,生出interface
透過介面,是無法看出完整atack行爲的
class NormalAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}class MagicAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}interface AttackType{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}3. Delegation/Composition 委派或複合
class UltimateAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}委派
hero委派atack職責,給attackType介面
class NormalAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}class MagicAttack{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}interface AttackType{
	+ attack(
    	attacker:Hero,
     	attacked:Hero
    ):void
}Hero
-------
hp:int
attackType:AttackType
-------
attack(hero:Hero):voidresulting context- 成功的依賴反轉
UltimateAttackNormalAttackMagicAttackAttackTypeHeroUltimateAttackNormalAttackMagicAttackHero因為依賴的方向確實被反轉了
原本hero 依賴attack行為區塊
resulting context-達到1+1~=2的效果
最厲害的是透過DI的方式
在不修改Context內部程式碼的前提之下
不斷地擴充新的handler來支援新的需求(OCP)
Context
Handler
Handler
Handler
Handler
n 倍效率
學會察覺到Forces
真正對軟體設計入木三分的人所設計出的軟體
沒有一行程式碼是多餘的, 要怎麼做到這件事呢?
需要大量的練習,藉由一次次的經驗
來鍛鍊察覺forces的能力,
並且清晰地說出你究竟是套用了何種pattern,來解決forces
避免Over Design
| 工程師技能 | 戰鬥技能 | 
|---|---|
| 熟習程式語言 | 強壯身體 | 
| 熟悉後端知識 | 懂武術 | 
| solid + ooad | 懂排陣法 | 
| Clean Arch | 懂兵法 | 
目標: 解耦合高內聚
目標: 贏的漂亮
- 
	got a require document 
- 
	OOA 
- 
	OOP version 1 
- 
	feel something wrong! find out force and problem 
- 
	OOD use design pattern solve force 
- 
	OOP version 2 
You got a message!
Every design needs to be drawn first! remember forever!
Architecture thinking: text to tech
The architectural thinking of software engineering is based on the relationship of text to objects and classes.
Thank You!
Questions?
OOD
TODO
SOLID
TODO
Behavioral
TODO
Structural
TODO
Creational
Architecture
OO
By Shen Hoh
OO
- 90
 
   
   
  