PHP design pattern (4) prototype mode prototype example details

Time:2020-11-20

This article describes the PHP design pattern: prototype pattern prototype. For your reference, the details are as follows:

1. Overview

As we all know, the creation pattern is generally used to create a new object, and then we use this object to complete some object operations. We can quickly create an object through the prototype pattern, and we can quickly complete the object creation without providing a special new () operation. This is undoubtedly a very effective way to quickly create a new object.

Example 1: the monkey king plucks the monkey’s hair and blows it gently to make a lot of Monkey King.

Example 2: send it by express

Here’s a post express scenario:
“Send me an express.” The customer said.
“To where? To… ” You ask.
“It’s almost the same as last time. It’s just mailed to another address. Here’s the mailing address…” The customer says and gives you a note with a mailing address.
“Good!” You happily agree, because you have saved the user’s previous mailing information, you can quickly create new express data by simply copying the data and then simply modifying it.

2. Problems

When the constructor of an object is very complex, it takes a lot of time and resources to generate a new object? How do we create it?

3. Solutions

Create more objects of the same type by copying (clone, copy) an object of the specified type. This specified object can be called a “prototype” object, that is, by copying the prototype object to get more objects of the same type. Prototype design pattern. Many template libraries in PHP use clone. Such as Smarty.

4. Applicability

The main idea of prototype pattern is to clone a new object based on the existing object. Generally, a clone method is provided inside the object, and a copy of the object is returned through this method. This way of creating an object is different from the previous creation patterns. The factory pattern and abstract factory described above are both factory encapsulated The process of the new operation of the body returns a new object. Sometimes it is not worth creating an object through such a creation factory. Especially in the following scenarios, it may be simpler and more efficient to use the prototype mode.

When a system should be independent of its product creation, composition and representation, prototype mode should be used

2) when the class to be instantiated is specified at runtime, for example, by dynamic loading;

3) in order to avoid creating a factory class level parallel to the product class level

When an instance of a class can only have one of several different combinations of states. It may be more convenient to build a corresponding number of prototypes and clone them than to instantiate the class manually each time with the appropriate state. (that is, when we are dealing with some objects relatively simple, and the difference between objects is very small, maybe only a few fixed attributes are different, maybe we use the prototype pattern more appropriately).

5. Structure

The structure of the prototype pattern is shown in the figure above on the following page:

6. Composition

Client role: a client program that uses prototype objects
Abstract prototype role: Specifies the interface that the concrete prototype object must implement (if you want to provide deep copy, you must have the rule of implementing clone)
Concrete prototype: derived from the Abstract prototype, it is the object used by the client program, that is, the copied object. This role needs to implement the interface required by the Abstract prototype role.

7. Effect

The prototype pattern has many of the same effects as abstract factory and builder patterns: it hides specific product classes from customers, thus reducing the number of names customers know. In addition, these patterns enable customers to use application specific classes without changing them.

Here are some other advantages of prototype mode.

1) add and delete products at runtime: prototype allows a new specific product class to be incorporated into the system only by registering prototype instances with customers. It is more flexible than other creative patterns because customers can build and delete prototypes at run time.
2) change values to specify new objects: highly dynamic systems allow you to define new behaviors through object composition – for example, by specifying values for an object variable – without defining new classes. You can effectively define new class objects by instantiating existing classes and registering them as prototypes of client objects. The customer can delegate responsibility to the prototype to show new behavior. This design allows users to define new “classes” without programming. In fact, cloning a prototype is similar to instantiating a class. The prototype pattern can greatly reduce the number of classes required by the system.
3) Change structure to specify new objects: many applications create objects from assemblies and subassemblies.
4) Reducing the construction of subclasses, factory method often produces a creator class hierarchy parallel to the product class level. The prototype pattern allows you to clone a prototype rather than request a factory method to generate a new object. So you don’t need the creator class hierarchy at all. This advantage is mainly applicable to languages such as C + + that do not treat classes as primary class objects. Languages like Smalltalk and objective C benefit less because you can always use a class object as a generator. In these languages, class objects already act as prototypes.
5) Use classes to dynamically configure some runtime environments that allow you to load classes into your application dynamically. In languages like C + +, the prototype pattern is the key to taking advantage of this functionality. An application that wants to create an instance of a dynamically loaded class cannot refer to the constructor of the class statically. Instead, it should be up to the runtime to automatically create an instance of each class at load time and register the instance with the prototype Manager (see the implementation section). This allows the application to request instances of newly loaded classes from the prototype manager that were not originally connected to the program. E t + + application framework [WGM 8 8] has a running system that uses this scheme.

The main drawback of prototype is that every subclass of prototype must implement clone operation, which can be difficult.
For example, it is difficult to add clone operations when the class under consideration already exists. Cloning can also be difficult when you include objects that do not support copying or have circular references.

8. Implementation

<?php
/**
 *Prototype pattern 
 */
 
/**
 *Abstract archetypal roles
 */
interface Prototype {
  public function copy();
}
 
/**
 *Specific archetypal roles
 */
class ConcretePrototype implements Prototype{
 
  private $_name;
 
  public function __construct($name) {
    $this->_name = $name;
  }
 
  public function setName($name) {
    $this->_name = $name;
  }
 
  public function getName() {
    return $this->_name;
  }
 
  public function copy() {
    /**Deep copy*/
    return clone $this;  
    /**Light copy*/
    //return $this;  
  }
}
 
class Client {
 
   /**
   * Main program.
   */
  public static function main() {
    $object1 = new ConcretePrototype(11);
    $object_copy = $object1->copy();
 
    var_dump($object1->getName());
    echo '<br />';
    var_dump($object_copy->getName());
    echo '<br />';
 
    $object1->setName(22);
    var_dump($object1->getName());
    echo '<br />';
    var_dump($object_copy->getName());
    echo '<br />';
  }
}
Client::main();
?>

9. Shallow copy and deep copy

Schematic diagram of prototype pattern:

Light copy

All variables of the copied object have the same values as the original object, and references to other objects still point to the original object. In other words, it does not copy the current object.

Objects after shallow replication and object copies:

Deep copy

All variables of the copied object have the same values as the original object, except those that refer to other objects. Variables that refer to other objects will point to a new copied object instead of the original referenced object. In other words, deep copy copies all the objects referenced by the object to be copied once, and this kind of copy of the referenced object is called indirect copy.

Deep replicated objects and object copies:

How many layers of deep copy should go is an uncertain question.

When you decide to copy an object in a deep copy mode, you must decide whether to take a shallow copy or a deep copy or continue to use a deep copy for an indirectly copied object.

Therefore, when taking a deep copy, you need to decide how deep it is. In addition, in the process of deep copy, the problem of circular reference is likely to occur.

10. Prototype mode with prototype Manager

The second form of prototype pattern is the prototype pattern with prototype manager. Its UML diagram is as follows:

Prototype manager role: create specific prototype class objects and record each created object.

The following example shows that a user-defined color prototype is stored in the prototype manager, and the customer clones the color object through the prototype manager.

<?php
/**
 * abstract Prototype
 *
 */
abstract class ColorPrototype
{
 //Methods
 abstract function copy();
}
 
/**
 * Concrete Prototype
 *
 */
class Color extends ColorPrototype{
 //Fields
 private $red;
 private $green;
 private $blue;
 //Constructors
 function __construct( $red, $green, $red) {
  $this->red = $red;
  $this->green = $green;
  $this->blue = $red;
 }
 /**
  * set red
  *
  * @param unknown_type $red
  */
 public function setRed($red) {
  $this->red = $red;
 }
 
 /**
  * get red
  *
  */
 public function getRed(){
  return $this->red;
 }
 /**
  *set Green
  *
  * @param $green
  */
 public function setGreen($green) {
  $this->green = $green;
 }
 /**
  * get Green
  *
  * @return unknown
  */
 public function getGreen() {
  return $this->green ;
 }
 /**
  *set Blue
  *
  * @param $Blue
   */
 public function setBlue($Blue) {
  $this->blue = $Blue;
 }
 /**
  * get Blue
  *
  * @return unknown
  */
 public function getBlue() {
  return $this->blue ;
 }
 
 /**
 * Enter description here...
 *
 * @return unknown
 */
 function copy(){
 return clone $this;
 }
 
 function display() {
 echo $this->red , ',', $this->green, ',', $this->blue ,'<br>';
 }
}
/**
 * Enter description here...
 *
 */
class ColorManager
{
 // Fields
 static $colors = array();
 // Indexers
 public static function add($name, $value){
 self::$colors[$name] = $value;
 }
 
 public static function getCopy($name) {
 return  self::$colors[$name]->copy();
 }
}
/**
 *Client
 *
 */
class Client
{
 public static function Main()
 {
 //Prototype: white
 ColorManager::add("white", new Color( 255, 0, 0 ));
 
 //The red color can be obtained from the prototype white object, but the white is modified: R
 $red = ColorManager::getCopy('white');
 $red->setRed(255);
 $red->display();
 
 //Green can be obtained from the prototype white object, but the White: G
 $green = ColorManager::getCopy('white');
 $green->setGreen(255);
 $green->display();
 
 //The green can be obtained from the prototype white object, but the white is modified: B
 $Blue = ColorManager::getCopy('white');
 $Blue->setBlue(255);
 $Blue->display();
 }
}
ini_set('display_errors', 'On');
error_reporting(E_ALL & ~ E_DEPRECATED);
Client::Main();
?>

More about PHP related content interested readers can see this site topic: “PHP object-oriented programming introductory tutorial”, “PHP array (array) operation skills”, “PHP basic syntax introductory course”, “PHP operation and operator Usage Summary”, “PHP character string (string) Usage Summary”, “PHP + MySQL database operation introduction tutorial” and “PHP common database operation” Summary of writing skills

I hope this article will help you with PHP programming.

Recommended Today

MVC and Vue

MVC and Vue This article was written on July 27, 2020 The first question is: is Vue an MVC or an MVVM framework? Wikipedia tells us: MVVM is a variant of PM, and PM is a variant of MVC. So to a certain extent, whether Vue is MVC or MVVM or not, its ideological direction […]