Originally in the book Design Patterns, many design patterns encourage the use of loose coupling. To understand this concept, it's best to talk about the arduous journey that many developers go through working on large systems. When you change one piece of code, problems can occur, and cascading breaks can occur in other parts of the system—parts you once thought were completely unrelated.
The problem is tight coupling. Functions and classes in one part of the system are heavily dependent on the behavior and structure of functions and classes in other parts of the system. You want a set of patterns that allow these classes to communicate with each other, but you don't want to tie them tightly together to avoid interlocking.
In large systems, a lot of code depends on a few key classes. Difficulties may arise when these classes need to be changed. For example, suppose you have a User class that reads from a file. You want to change it to a different class that reads from the database, however, all your code references the original class that reads from the file. At this time, it will be very convenient to use factory mode.
Factory pattern is a class that has certain methods that create objects for you. You can use a factory class to create objects without using new directly. This way, if you want to change the type of object created, you only need to change the factory. All code using this factory is automatically changed.
Example 1: Display a list of factory classes. The server side of the equation consists of two parts: a database and a set of PHP pages that allow you to add feedback, request a feedback list, and get articles related to specific feedback.
interface IUser { function getName(); } class User implements IUser { public function __construct( $id ) { } public function getName() { return "Jack"; } } class UserFactory { public static function Create( $id ) { return new User( $id ); } } $uo = UserFactory::Create( 1 ); echo( $uo->getName()."\n" ); ?>
IUser interface defines what operations a user object should perform. The implementation of IUser is called User, and the UserFactory factory class creates IUser objects. This relationship can be represented by UML in Figure 1.
Figure 1. Factory class and its related IUser interface and user class
If you run this code on the command line using the php interpreter, you will get the following results:
% php factory1.php Jack %
The test code will request the User object from the factory , and output the result of the getName method.
There is a variant of the factory pattern that uses factory methods. These public static methods in a class construct objects of that type. This method is useful if it is important to create objects of this type. For example, suppose you need to create an object first and then set a number of properties. This version of the factory pattern encapsulates the process in a single location, so you don't have to copy complex initialization code and paste it all over the code base.
Example 2 shows an example of using factory methods.
interface IUser { function getName(); } class User implements IUser { public static function Load( $id ) { return new User( $id ); } public static function Create( ) { return new User( null ); } public function __construct( $id ) { } public function getName() { return "Jack"; } } $uo = User::Load( 1 ); echo( $uo->getName()."\n" ); ?>
This code is much simpler. It has only one interface IUser and a User class that implements this interface. The User class has two static methods for creating objects. This relationship can be represented by UML in Figure 2.
Figure 2. IUser interface and user class with factory method
Running the script on the command line produces the same result as Listing 1, as shown below:
% php factory2.php Jack %
As mentioned above, sometimes this Patterns may seem overkill in smaller environments. However, it's best to learn this solid form of coding that you can apply to projects of any size.
For more articles related to the Factory Pattern of PHP Design Patterns, please pay attention to the PHP Chinese website!