Factory model can be said to be one of our most widely used design patterns.
The so-called factory model is not an instance of the class by the customer class, but is implemented by the factory.
If the customer class client without the plant mode is to implement the use of the interface class Parent and his implementation class SON, you must implement the following code in the client:
Parent P = new Son ();
This dependency is:
As can be seen from the above figure, the customer class Client relies on the interface class Parent and its implementation class SON, this dependence is too strong. Such dependencies make us have to know which type of the specific implementation of the PARENT interface in the customer class. If the Parent's implementation class has SON, SON1, SON2, then we must always know which class is required in the client class.
Very nature, the client class as a user, it doesn't want to know when to implement which class, SON, SON1, or SON2; I only want to enter a parameter or keyword to get the specific implementation class of Parent; otherwise, customer class I don't know or not, regardless of the specific implementation of the interface, as long as the interface gets the implementation, then reach the specific function. This is exactly the work of factory model hopes.
Below us, we will specifically explain the solution to the above problems. Specifically, we only tell the simple factory model, then use it as a focus, we will expand the simple factory, which is combined with simple factories and Java reflection mechanisms to form the dynamic factory model to elaborate in our article. We may wish Become it a dynamic factory model.
In the elaboration of simple factories and dynamic factory patterns, we have used such an example or scenario: We have an Animal interface, it is very simple, only two methods: Eat () and Shout (), as follows:
Public Interface Animal
{
Public void Eat ();
Public void shout;
}
Then there are some Animal implementations: Checken, Dog, Sheep, etc. The following story is surrounded by this scene.
Now let's implement CHECKEN and DOG as follows:
Public class checken imports animal {
/ * (non-javadoc)
* @see animal # Eat ()
* /
Public void Eat () {
// Todo auto-generated method stub
System.out.println ("The Checken Is Eating Insect!);
}
/ * (non-javadoc)
* @see animal # shout ()
* /
Public void shout () {
// Todo auto-generated method stub
System.out.println ("The Checken Is Shouting Like 'Crow');
}
}
Public class dog imports animal {
/ * (non-javadoc)
* @see animal # Eat ()
* /
Public void Eat () {
// Todo auto-generated method stub
System.out.println ("THE DOG IS Eating Bone!);
}
/ * (non-javadoc)
* @see animal # shut () * /
Public void shout () {
// Todo auto-generated method stub
System.out.println ("The Dog Is Shouting Like 'Bark');
}
}
In this way, we don't use the factory model. If you want to get a dog, we must achieve the following code:
Animal Animal = New Dog ();
Animal.SHOUT ();
And let's use simple factory models, you want to get a dog called, it may be implemented like this:
Animal Animal = Factory.GetInstance ("DOG");
IF (Animal! = NULL)
{
Animal.SHOUT ();
}
The implementation of the Factory class is as follows:
Public class factory {
Public Static Animal GetInstance (String Name)
{
IF (Name.Equals ("DOG"))
{
Return New Dog ();
}
Else IF (Name.Equals ("Checken"))
{
Return new checken ();
}
Else
{
Return NULL;
}
}
}
It can be seen that the customer's class does hand over the instantiated work of the interface class to the Factory class, and the customer is instantiated, that is, if the customer enters "Dog", get new checken (), it also doesn't matter.
Let's take a look at the dependence of the simple factory:
It can be seen that the dependencies between Client and Checken, and DOG have been removed. Such results have been partially satisfied with object-oriented opening and closing principles and customers cannot rely on specific classes, but must rely on abstract principles.
The simple factory model completed the first abstraction of the customer's dependencies on the client, and then we can further abstract the factory, which is the content of the abstract factory model and factory method model, I don't have an explanation here.
It can be seen that simple factory models actually transfer the dependency of the customer class to the interface instance to the factory class. The fact that the factory's dependence on the interface is still very strong. As in the above example, the Factory class is seriously dependent on the Checken class and the Dog class, so dependence will still bring great trouble on the actual application.
For example, if we extends to the program, we add a Sheep class to implement an Animal interface, which is as follows:
Public class sheep imports animal {
/ * (non-javadoc)
* @see animal # Eat ()
* /
Public void Eat () {
// Todo auto-generated method stub
System.out.println ("THEEP IS Eating Grass!");
}
/ * (non-javadoc)
* @see animal # shout ()
* /
Public void shout () {
// Todo auto-generated method stub
System.out.println ("The Sheep Is Shouting Like 'BLAT');
}
}
Since the Factory class is seriously dependent on the realization of the Animal interface, we have added an implementation of an interface to modify the Factory class. As follows: public class factory {
Public Static Animal GetInstance (String Name)
{
IF (Name.Equals ("DOG"))
{
Return New Dog ();
}
Else IF (Name.Equals ("Checken"))
{
Return new checken ();
}
Else IF (Name.Equals ("sheep"))
{
Return new sheep ();
}
Else
{
Return NULL;
}
}
}
Here, we can see the shortcomings of simple factories: the factory's dependence is too strong, which is not conducive to the expansion of the system. That is, when there is a new product increasing, it has to modify the plant to increase support for new products. So do you have any way to break this plant's strong dependence on the product?
Let's take a look at the factory code, you can find that the only thing to do is to instantiate a product. Then we instantiate a class, in addition to using New, there is any other method?
We also say, in the reflection mechanism of Java, we get the class object of such a class, and then instantiate the classes using the newInstance () method of the Class object; and we get a class of Class The class name of the path is as a parameter.
In this way, our factory class can write this:
Public class factory {
Public Static Animal GetInstance (String Name)
{
Try
{
Class CLS = Class.Forname (Name);
Return (Animal) CLS.NEWINSTANCE ();
}
Catch (Exception E)
{
E.PrintStackTrace ();
Return NULL;
}
}
}
Very simple? Here, all our classes are in a directory. So our customer class code is:
Animal Animal = GetInstance ("DOG");
IF (Animal! = NULL)
{
Animal.SHOUT ();
}
If not in a directory, we can put all the products in a directory, then use a constant path to get the path of the product, then Class CLS = Class.Forname (Path Name);
In this way, with the help of the Java reflex mechanism, we realize dynamic factory models. Here, we may wish to call dynamic factory models.
The dynamic factory model has a good extension: 用, no matter how many products we increase, as long as all products are in a directory, we do not need to modify the factory. For example, we add an Animal's implementation class CAT, we only need to implement the CAT class without having to modify the Factory class.
It can be seen that it is used.
Java
The reflection mechanism makes our code a good extensibility. Similarly, everyone can look
Java API
The dynamic agent inside, is actually a proxy model
Java
The application of reflex mechanisms makes our agent models have good scalability. This can be applied to
AOP
In the case, the dynamic agent has become an important solution for solving surface-facing programming.