Home > Article > Backend Development > Detailed examples of 3 ways to automatically load PHP classes
Recently, I have been learning composer and found that I have encountered three methods of automatic loading of classes in PHP since I came into contact with PHP. These include the automatic loading method of PHP's own classes and the third method of PHP. The loading method of composer, a third-party dependency management tool, and the automatic loading method under PHP's Yaf framework. This blog mainly introduces the loading method that comes with PHP5 in detail. The automatic loading of classes under composer and Yaf will be divided into two parts to learn with you in the next time.
1. Manual loading method In languages such as C and C++, when you need to use related classes and methods in another file in PHP, you can use include,set_include_path() when loading, and you can also obtain the loading path through get_include_path(). Regarding set_include_path() and get_include_path(), I have just come into contact with them. Here I will only give a brief introduction to set_include_path(), and I will add more when I encounter problems in the future.
First of all, set_include_path() dynamically modifies the include_path in php.ini in the script, and this include_path is the pair of include and require (if no special explanation is given below, include means include and include_once, require represents the path of require and require_once) to be set, or predefined. If we need to use a.php, b.php, c.php... in the projname/home/lib/mylib/test folder in a main.php file, if the included path is not set , then write it in the following form:<?php include("projname/home/lib/mylib/test/a.php"); include("projname/home/lib/mylib/test/b.php"); include("projname/home/lib/mylib/test/c.php"); ......In this way, each include needs to contain an absolute path, which seems very troublesome. If you add set_include_path("projname/home/lib/mylib/test") before the file that needs to be included, then it can be written in the following form:
<?php set_include_path("projname/home/lib/mylib/test"); include("a.php"); include("b.php"); include("c.php"); ......Compared with the first method, it is time-consuming and laborious The second way of writing obviously saves a lot of time, but it still needs to include each file, it just simplifies the included path. Of course, the situation mentioned above is that the required files all exist in one folder. If the files exist in different folders, you can add multiple set_include_path() statements. At this time, if the files in include or require If the included file name appears in multiple directories, only the file that first appears in the set_include_path directory will be included; if there is no corresponding file in all the folders specified by set_include_path, and the file name happens to appear in the current folder , it directly includes the corresponding files in the current directory. The get_include_path() function is only suitable for obtaining the current include path. 2._autoload and spl_autoload_register() automatic loading methodsIn order to free both hands from the class loading method, an automatic loading mechanism is provided in PHP5 and later versions-- -autoload. Autoload allows classes to be loaded only when they are actually needed, which is called lazy loading, instead of including or requiring all class files from the beginning. The automatic loading mechanism provided by PHP is divided into two types---autoload() and spl_autoload_register(). 1). Autoload mechanism During the process of running the program in PHP5, if it is found that a certain class is not included, then the autoload automatic loading mechanism will be run to add the required The class is loaded in. It is written as follows:
<?php public function autoload($classname) { $fileName = $classname."php"; if (file_exist($fileName)) { require_once("$fileName"); } else { echo $fileName." doesn't exist!" } }According to the way this program is written, we can get the following conclusion:
The principle of ensuring the automatic loading mechanism is to make the class name and the file name have a corresponding relationship, class The name + suffix constitute the name of the file in which this class is located. If the file does exist, the class is loaded based on $fileName. If the file does not exist, the user is prompted that the file does not exist. In general, the automatic loading mechanism includes three steps:
Find the corresponding file on the disk according to the file name (the example is the simplest case, that is, the class and the PHP file that calls them are in the same directory); if they are not in the same directory , then you can use set_include_path() to specify the path to be loaded;
Load the disk file into the file system. This step is just to use general include and require to include the corresponding class file;
The principle of autoload() to implement automatic loading of classes is: there is a unified correspondence between class names and file names, which is the key to implementing autoload in a system. However, a system may be developed by different people. If there is no unified standard agreed before development, there may be different corresponding rules, which may lead to the need to implement multiple loading rules in autoload(), which may cause the autoload() function to Very bloated. In order to solve this problem, PHP also provides an automatic loading mechanism---spl_autoload_register().
2). spl_autoload_register() mechanism
SPL is Standard PHP Library (standard PHP library) The abbreviation of is an extension library introduced in PHP5. SPL autoload is implemented by pointing the function pointer autoload_func to the autoload function. SPL has two different autoloading functions, namely spl_autoload and spl_autoload_call. Different autoloading mechanisms can be implemented by pointing autoload_fun to the addresses of these two different loading functions.
spl_autoload
spl_autoload is the default automatic loading function implemented by SPL. It is a function that can accept two parameters. The first function is $class_name, which represents the name of the class to be loaded; the second parameter is $file_extension, which is an optional parameter and represents the extension of the class file. Multiple extensions can be specified in $file_extension. The extensions can be separated by semicolons. If no extension is specified, the default extension .inc or .php will be used. spl_autoload first changes $class_name to lowercase, and then searches for $class_name.inc or $class_name.php files in all include_paths. If the corresponding file is found, the corresponding class is loaded. In fact, you can manually use spl_autoload("xxxx", ".php") to load the xxxx class. This is actually similar to require/include, but spl_autoload is relatively more flexible because multiple extensions can be specified.
As mentioned earlier, the function pointer autoload_func contained in spl_autoload_register is used to specify the loading function to be used. Then, we must assign the corresponding function address to autoload_func. spl_autoload_register() implements the function of assigning a value to the function pointer autoload_func. If the spl_autoload_register() function does not contain any parameters, the default is to assign spl_autoload() to autoload_func.
spl_autoload_call
SPL module There is actually an autoload_functions inside, which is essentially a hash table, or for intuitive understanding, we imagine it as a container, and each element inside is a pointer to the loading function. The implementation mechanism of spl_autoload_call is actually relatively simple. It traverses the container in a certain order and executes the loading function pointed to by the function pointer inside. After each pointer is executed, it is checked whether the required class has been loaded. If loading is complete, exit. Otherwise, continue execution downwards. If after all loading functions are executed, the required classes are still not loaded, spl_autoload_call() exits directly. This means that even if the autoload mechanism is used, class loading may not be completed. The key lies in how you create your autoloading function.
Since there is an autoload_functions, how to add the created autoloading function to it? Same as spl_autoload, also use spl_autoload_register() to register the load function into autoload_functions. Of course, registered functions can be deleted from the hash table from autoload_functions through the spl_autoload_unregister() function. This is consistent with the factory design pattern written before
One thing that needs to be explained here is the order in which spl_autoload_register implements automatic loading. The automatic loading sequence of spl_autoload is: first determine whether autoload_func is empty. If autoload_func is empty, check whether the autoload function is defined. If it is not defined, return and report an error; if the autoload() function is defined, return the loading result. . If autoload_func is not empty, the function pointed to by the autoload_func pointer will be executed directly without checking whether autoload is defined. That is to say, the functions registered with spl_autoload_register() will be used first.
According to the above introduction, if autoload_func is non-empty, the autoload() function cannot be automatically executed. If you want to still use the autoload() function while using the spl_autoload_register() function, you can add the autoload function to the hash table through spl_autoload_register(), that is, spl_autoload_register(autoload()). The following code examples illustrate how to register ordinary methods and static public methods of a class respectively.
普通函数的注册方法。
<?php /** * @ 普通函数的调用方法,可以调用后缀名分别为.php和.class.php的类文件 */ function loadFielEndOfPhp($classname) { $fileName = $classname.".php"; if (file_exist($fileName)) { require_once("$fileName"); } else { echo $fileName." doesn't exist!" } } function loadFielEndOfClassPhp($classname) { $fileName = $classname.".class.php"; if (file_exist($fileName)) { require_once("$fileName"); } else { echo $fileName." doesn't exist!" } spl_autoload_register("loadFielEndOfPhp"); spl_autoload_register("loadFielEndOfClassPhp"); }
类中静态的加载函数的注册方法。
<?php /** * @ 类中静态成员函数的调用方法,可调用后缀名为.php和.class.php的文件 */ class test { public static function loadFielEndOfPhp($classname) { $fileName = $classname.".php"; if (file_exist($fileName)) { require_once("$fileName"); } else { echo $fileName." doesn't exist!" } } public static function loadFielEndOfClassPhp($classname) { $fileName = $classname.".class.php"; if (file_exist($fileName)) { require_once("$fileName"); } else { echo $fileName." doesn't exist!" } } spl_autoload_register(array("test","loadFielEndOfPhp")); //spl_autoload_register("test::loadFielEndOfPhp"); //上一行的另一种写法,不是使用数组的形式完成注册; spl_autoload_register(array("test","loadFielEndOfClassPhp")); //spl_autoload_register("test::loadFielEndOfClassPhp"); //第三行的另一种写法,不是使用数组的形式完成注册; }
The above is the detailed content of Detailed examples of 3 ways to automatically load PHP classes. For more information, please follow other related articles on the PHP Chinese website!