7

我的 PHP 库中有几个静态工厂模式。但是,内存占用正在失控,我们希望减少执行期间所需的文件数量。这是我们今天所处位置的一个示例:

require_once('Car.php');
require_once('Truck.php');

abstract class Auto
{
    // ... some stuff ...

    public static function Create($type)
    {
        switch ($type) {
            case 'Truck':
                return new Truck();
                break;
            case 'Car':
            default:
                return new Car();
                break;
        }
    }
}

这是不可取的,因为需要包含 Car.php 和 Truck.php,即使可能只需要其中一个。据我所知, require/include 及其 ..._once 变体包括与调用范围相同的库。这是真的?

如果是这样,我相信这会导致内存泄漏:

    abstract class Auto
    {
        // ... some stuff ...

        public static function Create($type)
        {
            switch ($type) {
                case 'Truck':
                    require_once('Truck.php');
                    return new Truck();
                    break;
                case 'Car':
                default:
                    require_once('Car.php');
                    return new Car();
                    break;
            }
        }
    }

在我看来,在第二个示例中,即使使用了 require_once 风格,对 Create() 的多次调用也会因为调用的范围而导致多次请求。

这是真的?在诸如此类的示例中,在 php 中动态包含库的最佳方法是什么?

谢谢!

4

4 回答 4

7

Autoload 工具通常被视为 Evil,但它在这些任务中工作得非常好。

如果您可以获得良好的文件系统 <-> 类名映射,那么您可以在给定要提供的类时找到它,那么它将节省您的开销并且仅在需要时加载类。

它也适用于静态类,因此一旦静态类在范围内,它甚至不需要调用一次 require 的“是否包含文件”测试,因为该类已经在符号表中。

然后你可以创建

require("autoloader.php"); 
$x = new Car();  
$x = new Bike(); 

它只会在需要时将它们带入。

有关详细信息,请参阅Php.net/__autoload

于 2008-11-05T21:42:46.990 回答
2

我建议使用自动加载器

也就是说,不要使用require_once()require 任何一个子类,而是允许自动加载器调用一个函数,该函数可以在您调用new Truck()或时加载引用的类new Car()

至于内存泄漏的问题,不,require_once不受代码块的限制。

于 2008-11-05T21:44:18.373 回答
1

看看__autoload() 函数

于 2008-11-05T21:43:56.127 回答
0

require_once 函数的要点是,无论范围如何,您都不会包含两次文件并重新定义导致 PHP 错误的类。所以不用担心内存泄漏,如果 require_once 被命中,类 def 只会进入全局符号表一次。

但除此之外,是的,使用自动加载器。

于 2008-11-05T22:11:03.407 回答