HomePHP Page 2 - Introducing the Flyweight Pattern with PHP 5
Defining a target class - PHP
Among the considerable variety of structural design patterns that can be implemented with PHP 4 (and PHP 5, by the way), there’s one in particular that deserves special attention. It's easy to apply in the context of a given web application, and it offers remarkable functionality when it comes to preventing the unnecessary instantiation of different classes. This two-part series covers that pattern.
To demonstrate a practical implementation of the flyweight design pattern with PHP 5, I'm going to start by creating a target class. This class will be used by a flyweight object to keep instances of that class limited to a specified number.
As you’ll see, any attempt to create new instances of the target class will result in returning the same object to calling code. Now, are you starting to understand how the flyweight pattern works? I’m sure you are!
Having explained the logic that I plan to follow in this case, here is the signature of the mentioned target class. It is tasked with constructing text input boxes as part of a form generator system. Have a look at it:
// define 'TextInputBox' class class TextInputBox{ private $name; private $size; private $maxlength; // assign default values for properties of input box public function __construct($name='default_name',$size=16, $maxlength=32){ if(!preg_match("/[a-zA-Z]+/",$name)){ throw new Exception('Invalid value for name property!'); } if(!is_int($size)||$size<0||$size>32){ throw new Exception('Invalid value for size property!'); } if(!is_int($maxlength)||$maxlength<16||$maxlength>64){ throw new Exception('Invalid value for maxlength property!'); } $this->name=$name; $this->size=$size; $this->maxlength=$maxlength; } // get (X)HTML markup of input text box public function getHTML(){ return '<input type="text" name="'.$this->name.'" size="'.$this->size.'" maxlength="'.$this->maxlength.'" />'; } }
As you can see, the signature for the above “TextInputBox” class is really simple to grasp. In short, all this class does is display a regular text input box, which comes in handy for constructing online forms.
Now that you have seen the definition for the previous target class, let me go one step further and create another one. This new class will be aimed specifically at displaying a conventional submit button, so it’s possible to build programmatically a simple contact form.
The definition for this brand new class is listed below, so pay attention to it:
// define 'SubmitButton' class class SubmitButton{ private $name; private $value; public function __construct($name='default_name',$value='Send Data'){ if(!preg_match("/[a-zA-Z]+/",$name)){ throw new Exception('Invalid value for name property!'); } if(!preg_match("/[a-zA-Z]+/",$value)){ throw new Exception('Invalid argument for value property!'); } $this->name=$name; $this->value=$value; } // get (X)HTML markup of submit button public function getHTML(){ return '<input type="submit" name="'.$this->name.'" value="'.$this->value.'" />'; } }
So far, so good. At this moment, I created two simple classes that are capable of rendering different elements of a web form. The question that comes up now is: how can they be put to work in tandem? That’s a good question!
To answer it, below I coded a short script that displays a simple contact form by using the two previous classes, which is comprised of three input boxes and the corresponding submit button as well. Here is the script in question:
As demonstrated above, the pair of classes that I created before were used to display a basic contact form that contains three input boxes, handy for letting users enter their respective first and last names, as well as their email addresses. So far, nothing unexpected, right?
But now, let me ask you the following question: what if you want to build a form generator application that only creates three instances of the previous “InputTextBox” class, no matter how many times you try to instantiate new objects?
Well, that’s where the flyweight pattern comes in. It’s possible to define a factory class that only returns to calling code, three instances of the same “InputTextBox” class that you learned previously. This implies that the instantiation of objects would be completely balanced inside the application.
Now, things are getting really exciting! Therefore, in the next few lines I’m going to show you how to create a flyweight factory class. As I stated before, it will be responsible for returning three unique instances of the previous “InputTextBox” class.
As usual, to learn how this flyweight class will be defined, read the following section.