Here is a detailed explanation why Abstract Classes are not same as Factory Method Pattern
Feature
Abstract Classes
Factory Method Pattern
Purpose
Define common behavior and enforce method implementation in subclasses.
Encapsulate object creation and allow subclasses to determine the concrete class to instantiate.
Usage
When you want to define a common interface and shared behavior among a group of related classes.
When the creation process is complex, varies between subclasses, or should be decoupled from client code.
Polymorphism
Yes, allows different subclasses to be treated uniformly.
Yes, but focuses on the creation process being polymorphic.
Code Reuse
Allows code reuse by defining common methods in the abstract class.
Separates creation logic from the business logic, allowing reuse of the creation process.
Encapsulation
Encapsulates common behavior and properties of subclasses.
Encapsulates object creation logic, making it easier to manage and change.
Client Code
Needs to know the specific subclass to instantiate.
Decoupled from concrete classes, only interacts with abstract creator and product interfaces.
Flexibility
Limited to defining behavior and properties; does not handle instantiation flexibility.
High, as it allows subclasses to change the class of objects that will be created without modifying the client code.
Extensibility
Adding new behavior requires modifying the abstract class or existing subclasses.
Adding new products requires creating new creator subclasses, without modifying existing client code.
Instantiation
Direct instantiation of subclasses, leading to tighter coupling between client code and concrete classes.
Uses a factory method to create objects, promoting loose coupling and adherence to the Open/Closed Principle.
Example Abstract Class in TypeScript
abstractclassDocument{abstractopen():void;abstractsave():void;abstractclose():void;print():void{console.log("Printing document");}}classWordDocumentextendsDocument{open():void{console.log("Opening Word Document");}save():void{console.log("Saving Word Document");}close():void{console.log("Closing Word Document");}}classPDFDocumentextendsDocument{open():void{console.log("Opening PDF Document");}save():void{console.log("Saving PDF Document");}close():void{console.log("Closing PDF Document");}}// Client codefunctionprocessDocument(doc:Document){doc.open();doc.save();doc.close();doc.print();}constwordDoc:Document=newWordDocument();processDocument(wordDoc);constpdfDoc:Document=newPDFDocument();processDocument(pdfDoc);
Example Factory Method Pattern in TypeScript
interfaceDocument{open():void;save():void;close():void;}classWordDocumentimplementsDocument{open():void{console.log("Opening Word Document");}save():void{console.log("Saving Word Document");}close():void{console.log("Closing Word Document");}}classPDFDocumentimplementsDocument{open():void{console.log("Opening PDF Document");}save():void{console.log("Saving PDF Document");}close():void{console.log("Closing PDF Document");}}abstractclassDocumentCreator{publicabstractcreateDocument():Document;publicnewDocument():void{constdoc=this.createDocument();doc.open();doc.save();doc.close();}}classWordDocumentCreatorextendsDocumentCreator{publiccreateDocument():Document{returnnewWordDocument();}}classPDFDocumentCreatorextendsDocumentCreator{publiccreateDocument():Document{returnnewPDFDocument();}}// Client codeclassApplication{publicstaticmain():void{letcreator:DocumentCreator;creator=newWordDocumentCreator();creator.newDocument();creator=newPDFDocumentCreator();creator.newDocument();}}Application.main();
By using this table and examples, you can see how abstract classes and the Factory Method pattern serve different purposes and how they can complement each other .
newDocument does not work without actually returning the document
letcreator:DocumentCreator;creator=newWordDocumentCreator();creator.newDocument();creator=newPDFDocumentCreator();// prevent access access to the WordDocument without removing the instance? creator.newDocument();
In my understanding assigning a new object to creator will override the accessor without removing the instance, so you will have no access to the object anymore and get a memory leak.
First, I updated the code of the article because in Typescript the Document is a built-in interface representing the HTML Document Object Model (DOM) interface .
Second, yes you can add newDocument to the abstract class and this will facilitates our code, Thank you for the information .
Third, Regarding your concern about memory leaks and object access:
Object Lifetime: Assigning a new object to creator does not remove the previous instance. It only changes the reference in the creator variable. The previous instance is still accessible through any other references or will be garbage collected if no references exist.
Returning the Document: In your example, newDocument returns the created document. This ensures that the client code can maintain a reference to the created document, preventing memory leaks and allowing continued access.
For further actions, you may consider blocking this person and/or reporting abuse
We're a place where coders share, stay up-to-date and grow their careers.
Here is a detailed explanation why
Abstract Classesare not same asFactory Method PatternExample Abstract Class in TypeScript
Example Factory Method Pattern in TypeScript
By using this table and examples, you can see how abstract classes and the Factory Method pattern serve different purposes and how they can complement each other .
Thank you much for your detailed explanation. Maybe this goes beyond the tasks I commonly used classes for. I just have still some questions:
Why did you not add newDocument to the abstract class like we would commonly do (this is JS syntax)? Isn´t this the task of an abstract class?
Did you use ChatGPT for the examples, as the code seems to have some issuses?
newDocument does not work without actually returning the document
In my understanding assigning a new object to creator will override the accessor without removing the instance, so you will have no access to the object anymore and get a memory leak.
Or did I get something wrong?
First, I updated the code of the article because in Typescript the Document is a built-in interface representing the HTML Document Object Model (DOM) interface .
Second, yes you can add newDocument to the abstract class and this will facilitates our code, Thank you for the information .
Third, Regarding your concern about memory leaks and object access:
Object Lifetime: Assigning a new object to creator does not remove the previous instance. It only changes the reference in the creator variable. The previous instance is still accessible through any other references or will be garbage collected if no references exist.
Returning the Document: In your example, newDocument returns the created document. This ensures that the client code can maintain a reference to the created document, preventing memory leaks and allowing continued access.