Beginners must have a lot of confusion about design patterns. Today is the weekend, so I took some time to write an article about single-piece mode combined with command chain mode to create the core of the system. Maybe for some people, the content of the article is too simple. , this is a tutorial for beginners, because time is tight (I have to go shopping with my wife, haha), there are irregularities in design, irregularity in code writing, bugs, etc. I hope all heroes can point them out for convenience. Let's make progress together. My level is limited.^_^
I believe that everyone has read many books or articles about applying design patterns in PHP, but few of them directly give examples. Most of them feel confused after reading them. I feel that without project practice, it is difficult to figure out the design pattern part.
In order to avoid the code being too complex, exception handling and other contents are not added.
For the basic knowledge of singleton mode and command chain mode, you can google it yourself. I won’t go into details. Let’s look at the example directly:
<?php
/*
*@author:NoAngels
*@time: August 30, 2008
*/
interfaceIRunAction{
//Get the methods defined in the class that can be run in the APP
static function LoadActions();
//The entry function in the class is used to call other functions in the class
function runAction($action, $args);
}
/*
*Core part of APP system
*/
classAPP{
static private $__instance = null;
static private $__commands = array();
static private $__flag = 1;
private function __construct(){}
//Single-piece mode design obtains the only instance of this class
static function Load(){
if(self::$__instance == null) self::$__instance = new APP;
return self::$__instance;
}
//Add naming to $__instance of APP. Every time you add a new command, check whether an instance of this class has been added before.
//If there is, ignore the operation. If not, add it.
public function addCommand($cmdName){
foreach(self::$__commands as $cmd){
if(strtolower(get_class($cmd)) == strtolower(get_class($cmdName))){
self::$__flag = 0;
break;
}
}
if(self::$__flag == 1) self::$__commands[] = $cmdName;
self::$__flag = 1;
}
//The core part of the command chain mode design calls the entry function of the instance
//First check whether calling this operation is allowed in the class. If not, it will prompt undefined operation and exit.
public function runCommand($action, $args){
self::$__flag = 0;
foreach(self::$__commands as $cmd){
if(in_array($action, $cmd->LoadActions())){
self::$__flag = 1;
$cmd->runAction($action, $args);
}
}
if(self::$__flag == 0){
self::$__flag = 1;
exit("undefined action by action : $action");
}
}
//To delete an instance of a class, just specify the name of the class.
public function removeCommand($className){
foreach(self::$__commands as $key=>$cmd){
if(strtolower(get_class($cmd)) == strtolower($className)){
unset(self::$__commands[$key]);
}
}
}
//For everyone's testing to see if the addition and deletion are successful
public function viewCommands(){
echo(count(self::$__commands));
}
}
//Class User implements interface IRunAction
class User implements IRunAction{
//Define operations that can be called
static private $__actions = array('addUser', 'modifyUser', 'removeUser');
//Get the operations that can be called. In the actual process, don't just love you directly. $__actions is designed as a public call.
//You should design a LoadActions function to get the value of $__actions
static public function LoadActions(){
return self::$__actions;
}
//Run the specified function
public function runAction($action, $args){
//If you don’t understand how to use this function, please refer to the manual.
call_user_func(array($this,$action), $args);
}
//Just a test function
protected function addUser($name){
echo($name);
}
}
//Test-like User
class Test implements IRunAction{
static private $__actions = array('addTest', 'modifyTest', 'removeTest');
static public function LoadActions(){
return self::$__actions;
}
public function runAction($action, $args){
call_user_func(array($this,$action), $args);
}
protected function addTest($name){
echo($name);
}
}
//The following is the test code
APP::Load()->addCommand(new User);
APP::Load()->addCommand(new User);
APP::Load()->addCommand(new User);
APP::Load()->addCommand(new User);
APP::Load()->runCommand('addUser', 'NoAngels');
APP::Load()->addCommand(new Test);
APP::Load()->runCommand('addTest', null);
The APP class is designed in singleton mode, which is the core part of the system. I believe you will know by looking at the code that the Load method is to load the APP class instance, which is equivalent to The getInstance static method in some books has three public methods: addCommand, runCommand, and removeCommand. runCommand is the core part. It is also the core startup program of the command chain mode. Please see the source code for the specific implementation. The code is written very clearly. I won’t go into details here.
Classes User and Test implement the interface IRunAction. Both classes define a static private variable $__actions, which is an array that contains operations that can be called by the runCommand function of the APP.
The following is the running process of the system:
APP startup
-------addCommand, add the class to which the operation to be run belongs to the APP. If the added class is designed using the singleton mode, you can add addCommand(SingletonClass::Load()) as follows. Otherwise, you can add it as follows Call
addCommand(new someClass)
-------runCommand. Run operations. For example, there is an operation addUser in the User class. I can directly enable runCommand($acttion, $args). Loop through the $__commands array in the APP. If there is an instance of one of the classes If you have this operation, call the runAction function of the instance. If you do not add an instance of a certain class using addCommand, you will be prompted for an undefined operation and exit.
The runAction in class User and class Test calls call_user_func, a very commonly used function. The corresponding function in this class is called.
Tip: This is the end of the explanation and examples. How do you understand it and how to use this idea? Just see It’s your own understanding that you have to do everything yourself. (ps: It can be made into a single entry file in the framework. Whether or not to implement MVC depends on what you think.)