Introduccion
Dónde estamos y hacia dónde vamos
Patrones creacionales
Singleton
Singleton 101
Implementación de Singleton en JS
Contrastemos: Singleton con TS
Singleton: pros y contras
Factory
Factory 101
Diagrama de implementación de Factory
Implementación de Factory en JS
Contrastemos: Factory en TS
Factory: pros y contras
Abstract Factory
Abstract Factory 101
Diagrama de implementación de Abstract Factory
Implementación de Abstract Factory en JS
Contrastemos: Abstract Factory en TS
Abstract Factory: pros y contras
Builder
Builder 101
Diagrama de implementación de Builder
Implementación de Builder en JS
Contrastemos: Builder en TS
Builder: pros y contras
Prototype
Prototype 101
Diagrama de implementación de Prototype
Implementación de Prototype en JS
Contrastemos: Prototype en TS
Prototype: pros y contras
Conclusiones
¿Qué sigue sobre patrones de diseño?
No tienes acceso a esta clase
¡Continúa aprendiendo! Únete y comienza a potenciar tu carrera
El patrón Builder es una herramienta valiosa que aporta diversas ventajas al desarrollo de software. Este patrón permite construir objetos de manera flexible y modular, lo que puede resultar en código más ordenado y mantenible. Aquí algunas de sus principales ventajas:
Estas características hacen del patrón Builder una opción excelente para gestionar la creación de objetos complejos en tus proyectos.
Aunque el patrón Builder ofrece múltiples beneficios, también tiene algunas desventajas que deben considerarse:
El uso responsable de este patrón y un buen diseño de la solución ayudan a mitigar estos inconvenientes, garantizando un uso eficiente del patrón Builder.
Este patrón es especialmente útil en situaciones donde se busca un control más preciso sobre la construcción de objetos complejos. Algunos casos concretos donde es recomendable su utilización incluyen:
El patrón Builder es también popular en la construcción de consultas para bases de datos, donde es necesario construir paso a paso cadenas complejas adaptadas a diferentes sistemas de gestión de bases de datos.
Un reto práctico siempre es una excelente manera de consolidar conocimientos. En el contexto de aprender sobre el patrón Builder, se propone crear una línea de producción para un tipo de vehículo específico, como un Hatchback, utilizando las herramientas y métodos apropiados. Además, se invita a desarrollar una variante deportiva, promoviendo la creatividad y la adaptación del código.
La implementación de este reto no solo refuerza la comprensión del patrón Builder, sino que también permite experimentar con la creación y adaptación de nuevas versiones. Comparte tus logros y modificaciones con la comunidad, promoviendo el aprendizaje colaborativo y la mejora continua en el diseño de software.
Aportes 9
Preguntas 0
Le hice un custom a la solucion de la prueba, donde por medio de la funcion que se inicializadora, agrega dinamicamente las caracteristicas de un fordFiesta HB de esta forma permite seguir creando mas carros HB con las caracteristicas que se requieran:
interface Carro{
edition : string;
model:string;
airBags: number;
color:string;
}
interface HBProductionLine{
car: Carro;
internalModel: string;
setAirBags(airbags:number) :any;
setColor(color:string):any;
setEdition(edition:string):any;
resetProductLine():void
build():Carro
}
type ModelCar = {model:string}
class HBFordFiestaProductionLine implements HBProductionLine{
car: Carro = {
edition : "",
model:"",
airBags: 0,
color:""
};
internalModel: string = "";
constructor({model}: ModelCar){
this.car.model = model;
this.setInternalModel(model);
this.resetProductLine()
}
setAirBags(airbags: number) {
this.car.airBags = airbags;
}
setColor(color: string) {
this.car.color = color;
}
setEdition(edition: string) {
this.car.edition = edition;
}
setInternalModel(model:string){
this.internalModel = model;
}
resetProductLine(): void {
if(this.internalModel){
}
}
build(): Carro {
return this.car;
}
}
class CarroFordHB implements Carro{
edition: string;
model: string;
airBags: number;
color: string;
constructor(edition: string, model: string, airBags: number, color: string){
this.airBags = airBags;
this.model = model;
this.color = color;
this.edition = edition;
}
}
class Orquestator {
buildCarFordHB(car: CarroFordHB): CarroFordHB {
const HBFordFiesta = new HBFordFiestaProductionLine({model: car.model})
HBFordFiesta.setAirBags(car.airBags);
HBFordFiesta.setColor(car.color);
HBFordFiesta.setEdition(car.edition);
return HBFordFiesta.build()
}
}
const main = (orq:Orquestator) =>{
const carFordFiesta = new CarroFordHB("st","2018",2,"grey");
const carBuilderFord = orq.buildCarFordHB({airBags: carFordFiesta.airBags, color: carFordFiesta.color, edition: carFordFiesta.edition, model: carFordFiesta.model})
console.log(carBuilderFord) // { edition: 'st', model: '2018', airBags: 2, color: 'grey' }
}
main(new Orquestator())
Comparto mi solución n.n
type AvailableColors =
| "red"
| "black"
| "gray"
| "blue"
| "sky blue"
| "white"
| "default";
// STEP 1
interface CarProductionLine {
setAirBags(howMany: number): CarProductionLine;
setColor(color: AvailableColors): CarProductionLine;
setEdition(edition: EditionsType): CarProductionLine;
resetProductionLine(): void;
}
// STEP 2
type CarCatalog = "mastodon" | "rhino";
type ConstructorParams = { modelToCustomizeInLine: CarCatalog };
type EditionsType = "cvt" | "signature" | "sport" | "default";
class SedanProductionLine implements CarProductionLine {
private sedanCar!: BaseCar;
private modelToCustomizeInLine!: CarCatalog;
constructor({ modelToCustomizeInLine }: ConstructorParams) {
this.setModelToBuild(modelToCustomizeInLine);
this.resetProductionLine();
}
setAirBags(howMany: number): SedanProductionLine {
this.sedanCar.airBags = howMany;
return this;
}
setColor(color: AvailableColors): SedanProductionLine {
this.sedanCar.color = color;
return this;
}
setEdition(edition: EditionsType): SedanProductionLine {
this.sedanCar.edition = edition;
return this;
}
setModelToBuild(model: CarCatalog) {
this.modelToCustomizeInLine = model;
}
resetProductionLine() {
this.sedanCar =
this.modelToCustomizeInLine === "mastodon"
? new MastodonSedanCar()
: new RhinoSedanCar();
}
build(): BaseCar {
const sedanCar = this.sedanCar;
this.resetProductionLine();
return sedanCar;
}
}
class HatchBackProductionLine implements CarProductionLine {
private hatchbackCar!: BaseCar;
private modelToCustomizeInLine!: CarCatalog;
constructor({ modelToCustomizeInLine }: ConstructorParams) {
this.setModelToBuild(modelToCustomizeInLine);
this.resetProductionLine();
}
setAirBags(howMany: number): HatchBackProductionLine {
this.hatchbackCar.airBags = howMany;
return this;
}
setColor(color: AvailableColors): HatchBackProductionLine {
this.hatchbackCar.color = color;
return this;
}
setEdition(edition: EditionsType): HatchBackProductionLine {
this.hatchbackCar.edition = edition;
return this;
}
setModelToBuild(model: CarCatalog) {
this.modelToCustomizeInLine = model;
}
resetProductionLine() {
this.hatchbackCar =
this.modelToCustomizeInLine === "mastodon"
? new MastodonHatchbackCar()
: new RhinoHatchbackCar();
}
build(): BaseCar {
const hatchbackCar = this.hatchbackCar;
this.resetProductionLine();
return hatchbackCar;
}
}
// STEP 3
class BaseCar {
private _edition!: EditionsType;
private _model!: string;
private _airBags: number = 2;
private _color: AvailableColors = "black";
set airBags(howMany: number) {
this._airBags = howMany;
}
set color(color: AvailableColors) {
this._color = color;
}
set edition(edition: EditionsType) {
this._edition = edition;
}
set model(model: string) {
this._model = model;
}
}
class MastodonSedanCar extends BaseCar {
constructor() {
super();
this.model = "sedan";
}
}
class RhinoSedanCar extends BaseCar {
constructor() {
super();
this.model = "sedan";
}
}
class MastodonHatchbackCar extends BaseCar {
constructor() {
super();
this.model = "hatchback";
}
}
class RhinoHatchbackCar extends BaseCar {
constructor() {
super();
this.model = "hatchback";
}
}
// STEP 4
export class Director {
private productionLine!: CarProductionLine;
setProductionLine(productionLine: CarProductionLine) {
this.productionLine = productionLine;
}
constructCvtEdition(): void {
this.productionLine
.setAirBags(4)
.setColor("sky blue")
.setEdition("cvt");
}
constructSignatureEdition(): void {
this.productionLine
.setAirBags(8)
.setColor("gray")
.setEdition("signature");
}
constructSportEdition(): void {
this.productionLine.setAirBags(1).setColor("white").setEdition("sport");
}
}
type modelCar = "sedan" | "hatchback";
function appBuilder(director: Director, model: modelCar) {
const productionsLines = {
sedan: SedanProductionLine,
hatchback: HatchBackProductionLine,
};
const ProductionLine = productionsLines[model];
const mastodonProductionLine = new ProductionLine({
modelToCustomizeInLine: "mastodon",
});
director.setProductionLine(mastodonProductionLine);
director.constructCvtEdition();
const mastodonModelCvt = mastodonProductionLine.build();
console.log(mastodonModelCvt);
director.constructSignatureEdition();
const mastodonModelSignature = mastodonProductionLine.build();
console.log(mastodonModelSignature);
director.constructSportEdition();
const mastodonModelSport = mastodonProductionLine.build();
console.log(mastodonModelSport);
}
appBuilder(new Director(), "hatchback");
Comparto mi codigo TS
// Types
type BaseColors = 'blue' | 'black' | 'white';
type Editions = 'CVT' | 'Signature' | 'Sport';
type CarModel = 'mastodon' | 'rhino';
// Interface productionLine
interface CarProductionLine {
setAirbags(number: number): CarProductionLine;
setColor(color: BaseColors): CarProductionLine;
setEdition(edition: Editions): CarProductionLine;
resetProductionLine(): void;
build(): BaseCar;
}
// BaseCar class
class BaseCar {
private _airbags: number = 2;
private _color: BaseColors = 'white';
private _edition!: Editions;
private _model!: string;
set airbags(number: number) {
this._airbags = number;
}
set color(color: BaseColors) {
this._color = color;
}
set edition(edition: Editions) {
this._edition = edition;
}
set model(model: string) {
this._model = model;
}
}
// Concrete model Class
class MastodonHatchbackCar extends BaseCar {
constructor() {
super()
this.model = 'Hatchback';
}
}
class RhinoHatchbackCar extends BaseCar {
constructor() {
super();
this.model = 'Hatchback';
}
}
// HatchBack concrete production Line
class HatchbackProductionLine implements CarProductionLine {
private _hatchbackCar!: BaseCar;
private _modelToBuild!: CarModel;
constructor(carModel: CarModel) {
this.modelTobuild(carModel);
this.resetProductionLine();
}
setAirbags(number: number): HatchbackProductionLine {
this._hatchbackCar.airbags = number;
return this
}
setColor(color: BaseColors): HatchbackProductionLine {
this._hatchbackCar.color = color;
return this;
}
setEdition(edition: Editions): HatchbackProductionLine {
this._hatchbackCar.edition = edition;
return this;
}
resetProductionLine(): void {
this._hatchbackCar =
this._modelToBuild === 'mastodon' ?
new MastodonHatchbackCar() :
new RhinoHatchbackCar();
}
modelTobuild(carModel: CarModel) {
this._modelToBuild = carModel;
}
build(): BaseCar {
const HatchbackCar = this._hatchbackCar;
this.resetProductionLine();
return HatchbackCar;
}
}
class Director {
private _productionLine!: CarProductionLine;
setProductionLine(productionLine: CarProductionLine) {
this._productionLine = productionLine;
}
constructCvt() {
this._productionLine
.setAirbags(4)
.setColor('blue')
.setEdition('CVT')
};
constructSignature() {
this._productionLine
.setAirbags(3)
.setColor('black')
.setEdition('Signature')
};
constructSport() {
this._productionLine
.setAirbags(2)
.setEdition('Sport')
.setColor('blue')
};
}
// Applications
// mastodon hatchback builder
function hatchBackMastodonBuilder(director: Director) {
if (!director) {
console.log('--- No director provided ---');
return;
}
const hatchBackMastodonProductionLine = new HatchbackProductionLine('mastodon');
director.setProductionLine(hatchBackMastodonProductionLine);
// CVT Construction
director.constructCvt();
const mastodonHatchbackCVT = hatchBackMastodonProductionLine.build()
console.log('--- MASTODON HATCHBACK CVT ---');
console.log(mastodonHatchbackCVT);
// Signature Construction
director.constructSignature();
const mastodonHatchbackSignature = hatchBackMastodonProductionLine.build()
console.log('--- MASTODON HATCHBACK SIGNATURE ---');
console.log(mastodonHatchbackSignature);
// Sport Construction
director.constructSport();
const mastodonHatchbackSport = hatchBackMastodonProductionLine.build()
console.log('--- MASTODON HATCHBACK SPORT ---');
console.log(mastodonHatchbackSport);
}
// rhino hatchback builder
function hatchBackRhinoBuilder(director: Director) {
if (!director) {
console.log('--- No director provided ---');
return;
}
const hatchBackRhinoProductionLine = new HatchbackProductionLine('rhino');
director.setProductionLine(hatchBackRhinoProductionLine);
// CVT Construction
director.constructCvt();
const rhinoHatchbackCVT = hatchBackRhinoProductionLine.build()
console.log('--- RHINO HATCHBACK CVT ---');
console.log(rhinoHatchbackCVT);
// Signature Construction
director.constructSignature();
const rhinoHatchbackSignature = hatchBackRhinoProductionLine.build()
console.log('--- RHINO HATCHBACK SIGNATURE ---');
console.log(rhinoHatchbackSignature);
// Sport Construction
director.constructSport();
const rhinoHatchbackSport = hatchBackRhinoProductionLine.build()
console.log('--- RHINO HATCHBACK SPORT ---');
console.log(rhinoHatchbackSport);
};
// Implementation
hatchBackMastodonBuilder(new Director);
hatchBackRhinoBuilder(new Director);
Solución 😄…
.
.
.
.
// General steps so as to build products
interface CarProductionLineTS {
setAirBags(howMany: number): CarProductionLineTS;
setColor(color: AvailableColors): CarProductionLineTS;
setEdition(edition: string): CarProductionLineTS;
resetProductionLine(): void;
}
// Concrete builders subclasses
type CarCatalog = "mastodon" | "rhino";
type ConstructorParams = { model: CarCatalog };
class SedanProductionLineTS implements CarProductionLineTS {
private sedanCar!: CarTS;
private internalModel!: CarCatalog;
constructor({ model }: ConstructorParams) {
this.setInternalModel(model);
this.resetProductionLine();
}
setAirBags(howMany: number): SedanProductionLineTS {
this.sedanCar.airBags = howMany;
return this;
}
setColor(color: AvailableColors): SedanProductionLineTS {
this.sedanCar.color = color;
return this;
}
setEdition(edition: string): SedanProductionLineTS {
this.sedanCar.edition = edition;
return this;
}
setInternalModel(model: CarCatalog) {
this.internalModel = model;
}
setModel() {
this.sedanCar.model = "sedan";
}
resetProductionLine(): void {
this.sedanCar =
this.internalModel === "mastodon"
? new MastodonCarTS()
: new RhinoCarTS();
}
build(): CarTS {
this.setModel();
const sedanCar = this.sedanCar;
this.resetProductionLine();
return sedanCar;
}
}
class HatchbackProductionLineTS implements CarProductionLineTS {
private hatchbackCar!: CarTS;
private internalModel!: CarCatalog;
constructor({ model }: ConstructorParams) {
this.setInternalModel(model);
this.resetProductionLine();
}
setAirBags(howMany: number): HatchbackProductionLineTS {
this.hatchbackCar.airBags = howMany;
return this;
}
setColor(color: AvailableColors): HatchbackProductionLineTS {
this.hatchbackCar.color = color;
return this;
}
setEdition(edition: string): HatchbackProductionLineTS {
this.hatchbackCar.edition = edition;
return this;
}
setInternalModel(model: CarCatalog) {
this.internalModel = model;
}
setModel() {
this.hatchbackCar.model = "hatchback";
}
resetProductionLine(): void {
this.hatchbackCar =
this.internalModel === "mastodon"
? new MastodonCarTS()
: new RhinoCarTS();
}
build(): CarTS {
this.setModel();
const hatchbackCar = this.hatchbackCar;
this.resetProductionLine();
return hatchbackCar;
}
}
// Implement product classes, these ones could not belong to the same interface
type AvailableColors = "red" | "black" | "gray" | "blue";
class CarTS {
private _edition!: string;
private _model!: string;
private _airBags: number = 2;
private _color: AvailableColors = "black";
set airBags(howMany: number) {
this._airBags = howMany;
}
set color(color: AvailableColors) {
this._color = color;
}
set edition(edition: string) {
this._edition = edition;
}
set model(model: string) {
this._model = model;
}
}
class MastodonCarTS extends CarTS {
constructor() {
super();
}
}
class RhinoCarTS extends CarTS {
constructor() {
super();
}
}
// Implement director class
class DirectorTS {
private productionLine!: CarProductionLineTS;
setProductionLine(productionLine: CarProductionLineTS) {
this.productionLine = productionLine;
}
constructCvtEdition(): void {
this.productionLine.setAirBags(4).setColor("blue").setEdition("CVT");
}
constructSignatureEdition(): void {
this.productionLine.setAirBags(8).setColor("gray").setEdition("Signature");
}
constructSportEdition(): void {
this.productionLine.setAirBags(12).setColor("black").setEdition("Sport");
}
}
function appBuilderTS(director: DirectorTS) {
const mastodonSedanProductionLine = new SedanProductionLineTS({
model: "mastodon",
});
director.setProductionLine(mastodonSedanProductionLine);
director.constructCvtEdition();
const mastodonSedanCvt = mastodonSedanProductionLine.build();
console.log(mastodonSedanCvt);
director.constructSignatureEdition();
const mastodonSedanSignature = mastodonSedanProductionLine.build();
console.log(mastodonSedanSignature);
director.constructSportEdition();
const mastodonSedanSport = mastodonSedanProductionLine.build();
console.log(mastodonSedanSport);
const mastodonHatchbackProductionLine = new HatchbackProductionLineTS({
model: "mastodon",
});
director.setProductionLine(mastodonHatchbackProductionLine);
director.constructCvtEdition();
const mastodonHatchbackCvt = mastodonHatchbackProductionLine.build();
console.log(mastodonHatchbackCvt);
director.constructSignatureEdition();
const mastodonHatchbackSignature = mastodonHatchbackProductionLine.build();
console.log(mastodonHatchbackSignature);
director.constructSportEdition();
const mastodonHatchbackSport = mastodonHatchbackProductionLine.build();
console.log(mastodonHatchbackSport);
const rhinoSedanProductionLine = new SedanProductionLineTS({
model: "rhino",
});
director.setProductionLine(rhinoSedanProductionLine);
director.constructCvtEdition();
const rhinoSedanCvt = rhinoSedanProductionLine.build();
console.log(rhinoSedanCvt);
director.constructSignatureEdition();
const rhinoSedanSignature = rhinoSedanProductionLine.build();
console.log(rhinoSedanSignature);
director.constructSportEdition();
const rhinoSedanSport = rhinoSedanProductionLine.build();
console.log(rhinoSedanSport);
const rhinoHatchbackProductionLine = new HatchbackProductionLineTS({
model: "rhino",
});
director.setProductionLine(rhinoHatchbackProductionLine);
director.constructCvtEdition();
const rhinoHatchbackCvt = rhinoHatchbackProductionLine.build();
console.log(rhinoHatchbackCvt);
director.constructSignatureEdition();
const rhinoHatchbackSignature = rhinoHatchbackProductionLine.build();
console.log(rhinoHatchbackSignature);
director.constructSportEdition();
const rhinoHatchbackSport = rhinoHatchbackProductionLine.build();
console.log(rhinoHatchbackSport);
}
appBuilderTS(new DirectorTS());
¿Quieres ver más aportes, preguntas y respuestas de la comunidad?