Mon, Feb 23rd, 2009
PHP自动加载class文件的方案
PHP5中有一个很方便的__autoload的魔术函数,PHP Manual中的示例如下:
function __autoload($class_name) { require_once $class_name . '.php'; } $obj = new MyClass1(); $obj2 = new MyClass2();
算是很方便的一个函数,然而有一个缺陷就是没有名称空间,大量的class不得不放在一个目录下面,才可以用这个自动加载php的魔术函数,如果class文件要放在不同的目录里面,这个自动载入就无能为力了。为了解决这个问题,自己写了一个loadClass函数实现类似功能,代码如下:
function loadClass($tgt){ $class = substr($tgt, strrpos($tgt, '.')+1); require_once(DIR_APP.str_replace('.','/',$tgt).'.php'); return new $class(); } $test = loadClass("model.test"); $test->myfunc();
DIR_APP/model/test.php:
class test{ function myfunc(){ echo "hello, world!~"; } }
如此一来,就可以方便的加载在不同的目录里面的(缺点就是要打完整的”名称空间”),并且应该在PHP4中也可以使用(虽然PHP5已经是大流)……
补充@2009-02-23 22:42
就此自动载入的问题咨询了一下某飞,给了两个采用spl_autoload的自动载入的实现(by flying~):
function loader($className) { $classPath = str_replace('_', DIRECTORY_SEPARATOR, $className); require $classPath . '.php'; } spl_autoload_register('loader'); $user = new Model_User(); // load (inlcude paths):/Model/User.php
class的名称定义遵循PEAR标准用下划线_进行分隔
更加复杂点的支持多路径的”豪华版”(by flying~):
class Vifix_Loader { private static $paths = array(); public function addPath($path) { self::$paths[] = $path; } public function load($className) { $classPath = str_replace('_', DIRECTORY_SEPARATOR, $className) . '.php'; foreach (self::$paths as $path) { if (file_exists($path . $classPath)) { require $path . $classPath; } } } } spl_autoload_register(array('Vifix_Loader', 'load')); Vifix_Loader::addPath(dirname(__FILE__)); // ...
在下一般直接用 Zend_Loader 算了-_-bbb
-__-bbb
我是暂时放下php,现在要看马上计算机考试的内容了,只考frontpage制作静态页面,多年不用基本上都忘了……
貌似没难度 orz
很有难度,因为你不知道题目具体是要你怎么操作,基本上直接用html代码不算分,OTL
好吧,其实我想说会Word就会Frontpage -v-b
其实我想说的是,我一点也不懂。
今天做模拟题,我因为直接改代码而不是按书上教的,最后得0分 -v-b
@健康君: 其实HTML花个下午看看就能看明白了,然后CSS玩个一个星期左右就可以脱离所见即所得写网页了(当然,要好的网页则需要更长时间的练习就是了……)PHP的入门有一周左右的时间也差不多了(有编程基础更佳)
@Z君: 嘛嘛,想起自己二级Java考试时,因为通知给我个人的考试时间和考场地点均错误导致迟到45分钟,最后做某题要一个程序输出文件时时间不够再写程序,就用ultraedit伪造了一个 orz
突然发现,阁下前面的问题,貌似把 loadClass 的内容写入 __autoload 里即可-_-?(还能去掉 return new $class(); 一行=v=b)
不可行,__autoload是加载class所在的PHP文件,但是传递给__autoload的参数却是类名(没有“名称空间”导致的状况)
(所以其实阁下的那个代入__autoload才是正解——PHP Manual里面提到spl_autoload本来就是__autoload的默认实现 orz)
所以用 PEAR 标准的 Class Name 即可=v=b
这样Class Name也要写完整的 -v- 如下:
class Model_User{}
而如果使用loadClass,model.User的声明
class User{}
即可
所以在没有名称空间支持前还是全写=v=?
后面在下写的 autoload 也是要写全称=v=?
正是如此