定义:提供一个创建一系列相关或依赖对象的接口,而无需指定它们具体的类
类比:去买家具,一个家具套装包括桌子、椅子、沙发等,可以选择现代风格或者古典风格,整个套装都是统一风格的
应用场景
- 需要创建一系列相关或相互依赖的对象
- 系统需要独立于产品的具体类工作
优缺点
- 优点:
- 将客户端与具体类解耦
- 符合开闭原则,增加新的具体产品族时无需修改现有代码
- 缺点:
- 增加系统的抽象性和复杂性
- 增加了代码的数量,系统变得更庞大
实现代码
interface AbstractProductA {
usefulFunctionA(): string;
}
class ConcreteProductA1 implements AbstractProductA {
public usefulFunctionA(): string {
return 'The result of the product A1.';
}
}
class ConcreteProductA2 implements AbstractProductA {
public usefulFunctionA(): string {
return 'The result of the product A2.';
}
}
interface AbstractProductB {
usefulFunctionB(): string;
anotherUsefulFunctionB(collaborator: AbstractProductA): string;
}
class ConcreteProductB1 implements AbstractProductB {
public usefulFunctionB(): string {
return 'The result of the product B1.';
}
public anotherUsefulFunctionB(collaborator: AbstractProductA): string {
const result = collaborator.usefulFunctionA();
return `The result of the B1 collaborating with (${result})`;
}
}
class ConcreteProductB2 implements AbstractProductB {
public usefulFunctionB(): string {
return 'The result of the product B2.';
}
public anotherUsefulFunctionB(collaborator: AbstractProductA): string {
const result = collaborator.usefulFunctionA();
return `The result of the B2 collaborating with (${result})`;
}
}
interface AbstractFactory {
createProductA(): AbstractProductA;
createProductB(): AbstractProductB;
}
class ConcreteFactory1 implements AbstractFactory {
public createProductA(): AbstractProductA {
return new ConcreteProductA1();
}
public createProductB(): AbstractProductB {
return new ConcreteProductB1();
}
}
class ConcreteFactory2 implements AbstractFactory {
public createProductA(): AbstractProductA {
return new ConcreteProductA2();
}
public createProductB(): AbstractProductB {
return new ConcreteProductB2();
}
}
function clientCode(factory: AbstractFactory) {
const productA = factory.createProductA();
const productB = factory.createProductB();
console.log(productB.usefulFunctionB());
console.log(productB.anotherUsefulFunctionB(productA));
}
clientCode(new ConcreteFactory1());
clientCode(new ConcreteFactory2());