我在 php 中使用这个类进行自动加载。 http://pastebin.com/m75f95c3b
但是当我在某个地方
class Bar extends Foo
我有一个名为 foo.class.php 的文件,它找不到该类。但是当我将文件名更改为 Foo.class.php 时,它会找到该类。
我正在尝试向我的类添加一些功能,以便无论文件名是否以大写字母开头,都可以始终找到文件。但到目前为止我还没有成功。
任何人?
我在 php 中使用这个类进行自动加载。 http://pastebin.com/m75f95c3b
但是当我在某个地方
class Bar extends Foo
我有一个名为 foo.class.php 的文件,它找不到该类。但是当我将文件名更改为 Foo.class.php 时,它会找到该类。
我正在尝试向我的类添加一些功能,以便无论文件名是否以大写字母开头,都可以始终找到文件。但到目前为止我还没有成功。
任何人?
如果您的所有文件都有小写名称,请应用strtolower
到$className
类的每个方法中的变量值:
$className = strtolower($className);
但我建议您起草一些每个开发人员都必须遵守的编码指南。否则,您将不得不测试使用大写和小写字母编写文件名的 2 个<文件名长度>可能性中的每一个。
Gumbo 的解决方案是最好的,几乎每个人都在使用。我不明白你为什么不喜欢。当然你可以先检查类名大写的文件是否存在,如果不存在则检查小写版本是否存在。这绝对不比 Gumbo 的解决方案更好。毕竟“你的”程序员必须遵循一些约定/规则。
我或多或少会这样做
function __autoload($class_name) {
$upperName = strtoupper(substr($class_name,0,1)) . substr($class_name, 1);
$lowerName = strtolower(substr($class_name,0,1)) . substr($class_name, 1);
//Check to see if the class file exists as-is
if(file_exists($class_name . '.php')) {
require_once($class_name . '.php');
}elseif(file_exists($upperName . '.php')) {
require_once($upperName . '.php');
}elseif(file_exists($lowerName . '.php')) {
require_once($lowerName . '.php');
}else {
throw new Exception("The class $class_name could not be found.");
}
}
随着不同命名约定的出现,添加其他条件很容易。
我使用了一个 __autoload() 函数,该函数考虑了几种不同的文件命名约定,以提供与以前开发人员的向后兼容性。
它对每个约定执行一个简单的循环并检查该文件是否存在。如果文件存在,则加载它。
对于我的函数,我对不同的文件扩展名执行此操作,例如 .inc、.class 或 .inc.php 。你也可以这样做,但要搜索大写和小写的第一个字符。
我会将它放在 searchForClassFile() 方法中,在 else 部分带有注释“找到一个文件”。
编辑(更多信息):
我不是递归地进入类目录寻找正确的文件,而是将类名映射到特定位置。这是一种常见的做法。例如,foo_bar
映射到[CLASS_DIRECTORY]/foo/bar.[EXTENSION]
. 在我们的例子中,我们检查了几个不同的扩展。
在您的情况下,您必须就如何搜索类文件做出设计决定,但要修改您的代码:
} else {
// Found a file
if ($f == $className . self::$classFileSuffix ||
$f == strtolower($className) . self::classFileSuffix) {
return $subPath;
}
}
您可以编写一个仅降低第一个字符的函数,而不是 strtolower(),或者如果使用 PHP > 5.3.0(未正式发布),请使用 lcfirst() 函数。
您可以使用自动加载器扫描目录中的 .php 文件,并使用正则表达式实际查看每个文件的内容以查找诸如“类 Foo”之类的模式。当然,您需要缓存它,最好使用类 => 目录形式的数组。您还需要确保正确地使缓存无效,例如当文件夹中有新的 .php 文件时。
我为我的网站做这个,效果很好。