Skip to content
On this page

1.创建型模式(creational 5)

1.1 工厂模式(factory)

  • 定义一个创建对象的接口,让子类决定具体实例化哪一个对象。
js
function Bmw(model, price, maxSpeed) {
	this.model = model
	this.price = price
	this.maxSpeed = maxSpeed
}
function bmwFactory(type) {
	if (type === 'x5') {
		return new Bmw(type, 108000, 300)
	}
	if (type === 'x6') {
		return new Bmw(type, 111000, 320)
	}
}

测试用例

js
const expect = require('chai').expect
const bmwFactory = require('../tmp')

describe('工厂模式测试', () => {
	it('宝马', () => {
		var x5 = bmwFactory('x5')
		var x6 = bmwFactory('x6')

		expect(x5.price).to.equal(108000)
		expect(x6.price).to.equal(111000)
		expect(x5.maxSpeed).to.equal(300)
		expect(x6.maxSpeed).to.equal(320)
	})
})

es6 写法

js
class Bmw {
	constructor(model, price, maxSpeed) {
		this.model = model
		this.price = price
		this.maxSpeed = maxSpeed
	}
}

class BmwFactory {
	static create(type) {
		if (type === 'x5') {
			return new Bmw(type, 108000, 300)
		}
		if (type === 'x6') {
			return new Bmw(type, 111000, 320)
		}
	}
}

export default BmwFactory

测试用例

js
import BmwFactory from '../tmp'
const expect = require('chai').expect

describe('工厂模式 es6 测试', () => {
	it('创建X5的实例', () => {
		const x5 = BmwFactory.create('X5')
		expect(x5.model).to.equal('X5')
	})
	it('X5价格设置', () => {
		const x5 = BmwFactory.create('X5')
		expect(x5.price).to.equal(108000)
	})
})

1.2 抽象工厂(abstract-factory)

  • 定义了一个接口用于创建相关或有依赖关系的对象族,而无需明确指定具体类。
    • 解决了工厂方法模式的问题:在抽象工厂中只需要传入参数就可以实例化不同类型的工厂对象。
js
//机器人工厂
function droidProducer(kind) {
	if (kind === 'battle') return battleDroidFactory
	return pilotDroidFactory
}

function battleDroidFactory() {
	return new B1()
}

function pilotDroidFactory() {
	return new Rx24()
}

function B1() {}
B1.prototype.info = function () {
	return 'B1,Battle Droid'
}

function Rx24() {}
Rx24.prototype.info = function () {
	return 'Rx24,Pilot Droid'
}

module.exports = droidProducer

测试用例

js
const expect = require('chai').expect
const droidProducer = require('../tmp')

describe('抽象工厂测试', () => {
	it('战斗机器人', () => {
		const battleDroid = droidProducer('battle')()
		expect(battleDroid.info()).to.equal('B1,Battle Droid')
	})
	it('飞行机器人', () => {
		const pilotDroid = droidProducer('pilot')()
		expect(pilotDroid.info()).to.equal('Rx24,Pilot Droid')
	})
})

es6 实现

js
function droidProducer(kind) {
	if (kind === 'battle') return battleDroidFactory
	return pilotDroidFactory
}

function battleDroidFactory() {
	return new B1()
}

function pilotDroidFactory() {
	return new Rx24()
}

class B1 {
	info() {
		return 'B1, Battle Droid'
	}
}

class Rx24 {
	info() {
		return 'Rx24, Pilot Droid'
	}
}

export default droidProducer
js
const expect = require('chai').expect
import droidProducer6 from '../tmp'

describe('抽象工厂es6 测试', () => {
	it('战斗机器人 es6', () => {
		const battleDroid = droidProducer6('battle')()
		expect(battleDroid.info()).to.equal('B1, Battle Droid')
	})

	it('飞行机器人 es6', () => {
		const pilotDroid = droidProducer6('pilot')()
		expect(pilotDroid.info()).to.equal('Rx24, Pilot Droid')
	})
})

1.3 单例模式(singleton)

  • 确保一个类最多只有一个实例,并提供一个全局访问点 (预加载 懒加载?)
js
function Person() {
	if (typeof Person.instance === 'object') return Person.instance

	Person.instance = this
	return this
}

module.exports = Person

测试用例

js
const expect = require('chai').expect
const Person = require('../tmp')

describe('单例模式测试', () => {
	it('单个实例', () => {
		var john = new Person()
		var john2 = new Person()

		expect(john).to.equal(john2)
	})
})

es6 实现

js
class Person {
	constructor() {
		if (typeof Person.instance === 'object') {
			return Person.instance
		}
		Person.instance = this
		return this
	}
}

export default Person
js
const expect = require('chai').expect
import Person from '../tmp'

describe('单例模式测试 es6', () => {
	it('单个实例 es6', () => {
		var john = new Person()
		var john2 = new Person()

		expect(john).to.equal(john2)
		expect(john === john2).to.be.true
	})
})

1.4 建造者模式(builder)

  • 将一个复杂的对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
js
//对象构建
function Request() {
	this.url = ''
	this.method = ''
	this.payload = ''
}
//每个不同的表示 return this 支持链式调用
function RequestBuilder() {
	this.request = new Request()
	this.forUrl = function (url) {
		this.request.url = url
		return this
	}
	this.useMethod = function (method) {
		this.request.method = method
		return this
	}
	this.payload = function (payload) {
		this.request.payload = payload
		return this
	}
	this.build = function () {
		return this.request
	}
}
module.exports = RequestBuilder
js
const expect = require('chai').expect
const RequestBuilder = require('../tmp')

describe('建造者模式测试', () => {
	it('构建行为分离 method', () => {
		var requestBuilder = new RequestBuilder()
		var request = requestBuilder.forUrl('http://something/users').useMethod('GET').payload(null).build()

		expect(request.method).to.equal('GET')
	})
})

es6 实现

js
class Request {
	constructor() {
		this.url = ''
		this.method = ''
		this.payload = ''
	}
}
class RequestBuilder {
	constructor() {
		this.request = new Request()
	}
	forUrl(url) {
		this.request.url = url
		return this
	}
	useMethod(method) {
		this.request.method = method
		return this
	}
	payload(payload) {
		this.request.payload = payload
		return this
	}
	build() {
		return this.request
	}
}
export default RequestBuilder
js
const expect = require('chai').expect
import RequestBuilder from '../tmp'

describe('建造者模式 es6测试', () => {
	it('构建行为分离 es6', () => {
		const requestBuilder = new RequestBuilder()
		const url = 'http://something/users'
		const method = 'GET'
		const request = requestBuilder.forUrl(url).useMethod(method).payload(null).build()

		expect(request.method).to.equal(method)
		expect(request.payload).to.be.null
		expect(request.url).to.equal(url)
	})
})

1.5 原型模式(prototype)

  • 用原型实例指定创建对象的种类,并通过拷贝这些原型创建新的对象。
js
function Sheep(name, weight) {
	this.name = name
	this.weight = weight
}

Sheep.prototype.clone = function () {
	return new Sheep(this.name, this.weight)
}

module.exports = Sheep
js
const expect = require('chai').expect
const Sheep = require('../tmp')

describe('原型模式 测试', () => {
	it('sheep', () => {
		var sheep = new Sheep('dolly', 10.3)
		var dolly = sheep.clone()
		expect(dolly.name).to.equal('dolly')
	})
})

es6 实现

js
class Sheep {
	constructor(name, weight) {
		this.name = name
		this.weight = weight
	}
	clone() {
		return new Sheep(this.name, this.weight)
	}
}

export default Sheep
js
const expect = require('chai').expect
import Sheep from '../tmp'

describe('原型模式 es6测试', () => {
	it('sheep', () => {
		var sheep = new Sheep('dolly', 10.3)
		var dolly = sheep.clone()

		expect(dolly.name).to.equal('dolly')
		expect(dolly.weight).to.equal(10.3)
		expect(dolly).to.be.instanceOf(Sheep)
		expect(dolly === sheep).to.be.false
	})
})

Released under the MIT License.