PHP 5之前的版本,如果实例化一个不存在的类的对象,或者调用一个不存在的类的内不的静态方法将会导致一个致命错误。这意味着需要事先引入所有可能被使用的类文件,更好的办法是在被需要时才引入文件——为了不漏掉文件,就需要一个复杂的文件引入机制来处理外部文件的引入。
为了解决这个问题,PHP5中的“autoload”特性,可以实现“自动载入”,也就是按需载入文件。当试图对一个不存在的类进行类型暗示、静态调用,或者试图实例化一个对象,PHP就会使用调用__autoload()这个全局函数试图载入这个类文件。如果在调用autoload()后,类还是没有定义,解释器会停止工作并且抛出一个致命错误。
function __autoload($class) { // 需要 PEAR-compatible 类库的支持 require_once str_replace("_", "/", $class); } $obj = new Some_Class();
当对Some_Class类进行实例化,__autoload()就会被调用,传入"Some_Class.php"作为参数$class的值。函数中会把下划线替换成斜杠并通过require_once()引入。
通过使用__autoload()对于单命名空间来说非常有帮助;它会按需载入类文件,因此,用不到的类文件就不会被载入。但是当你在编写复杂的代码和使用不同的的类库时(比如:PEAR和一些大型应用)调用__autoload()会变得很难操控,从而使程序变得庞大而缓慢。
Siemen注:说实话这块真的不是看的很明白。
幸好标准的PHP类库(SPL)提供了一个简单的解决办法,将autoloader堆砌在其自身的顶部。如果一个执行失败了,下一个autoloader会接着尝试载入,直到文件被载入或者产生一个致命错误。
默认的,SPL使用自己的autoloader,称为spl_autoload();这是内建函数,检查所有的引入路径的文件名是否与需要载入的类的名称小写符合,且扩展名是.inc, .php或者其他在spl_autoload_extenstions()中用都好隔开传入的扩展名列表。
另外,按需载入可以通过spl_autoload_register()来加入堆栈。第一次调用这个函数用来替换__autoload()——也就是说,如果已经存在一个用户自定义__autoload()就需要将其按顺序注册到SPL中以便继续运行:
sql_autoload_register('spl_autoload');
if (function_existed('__autoload')) {
spl_autoload_register('__autoload');
}