2013-05-06 43 views
8

首先,这是一个很长的一个,所以感谢您的阅读。PHP 5.4 vs 5.3:在同一文件中自动加载多个类

我的问题是类似这样的: Class not found in the same file

我有一个定制的框架,最初写于2008年的PHP 5和它已经升级多年来与PHP 5.3的工作。我一直在寻求5.4的兼容性,并遇到了严重的问题。

ORM层自动为每个数据库表生成类。这些类全部放在每个表的一个文件中,我们的自动加载器在需要时加载该文件。 例如,“公共”模式(postgresql)中的'customer'表将具有以下类: PublicCustomer,PublicCustomerDBReader,PublicCustomerDBWriter。 现在这可能不是理想的设置,但它是我们目前拥有的。

在PHP 5.3中,如果需要PublicCustomer,则文件将被包含,解析并且所有上述类都可用。因此,例如,如果在PublicCustomer上调用静态方法,并且该方法在PublicCustomerDBReader中调用了某些内容,则该方法可以正常工作,因为该类位于同一个文件中。

在PHP 5.4中,它看起来像是在核心中进行了一些优化。在上面的场景中:

  1. 在PublicCustomer中调用一个静态方法。

  2. 自动加载器查找并加载正确的文件。

  3. PHP解析器只解析它所需的位置; PublicCustomer类。它没有解析或实例化PublicCustomerDBReader类。我可以通过测试该类是否存在以及通过查看解析器是否在达到文件结束时(即该方法被调用时)来确认此事。

  4. 然后PublicCustomer中的方法尝试调用PublicCustomerDBReader中的方法。这失败了,因为我们的自动加载器已经需要一次文件。

在我看来,我有两个解决方案:

  1. 分开这些班列,以便有针对每一个文件(这将产生的文件数量巨大)
  2. 重新设计ORM层,因此不需要多个类。

我是否理解了上述问题?

有谁知道是否在PHP 5.4中进行了优化或更改会导致此行为?

有没有其他可能的解决方案来解决我没有考虑过的问题?

+2

你应该使用方法1.你有多少班?它不应该是很多工作。 PHP自动加载器基于与classnames \ namespaces相关的文件名\目录。 PHP中没有内置的包支持。无论如何,它应该让你的脚本更加模块化。为什么当只需要class2时,应用程序将不得不解析class1和class2? – mpm 2013-05-06 09:05:58

+0

有没有什么能够阻止你以一种为每个类创建单独文件的方式修改ORM?这应该很容易解决问题,反正会更好。 ;) – 2013-05-06 09:06:28

+0

我可以将这些类分离为单独的文件,但这显然会增加ORM中文件的数量。每个数据库表有5个类,所以这会增加5倍的文件数。我管理的一些数据库有300-400个表,这意味着〜2000个文件。显然这不是一个很好的设计,我只是想知道如何改变它向前发展。 – user2353938 2013-05-06 10:04:50

回答

1

将读写器类放在文件的开头。你也可以考虑提交一个错误报告,因为解析器只应该停止错误。

0

参照PHP Framework Interop Group及其自动加载标准PSR-0PSR-4每个类都必须有自己的文件,名称以.php结尾。即使你有成千上万的类,这对文件系统也不是问题。

随着文件不止一个类,你必须考虑以下几个方面:

  • 每个类的自动加载必须决定要加载的文件。如果文件中有多个类,则每个使用的类都会导致加载。类文件应该加载一次而不是更多,因为类不能重新声明。我不推荐使用它,但是您可以使用自己的自动加载器来处理此问题,该自动加载器会记住已加载的文件或加载的类的测试。
  • 放置在同一个文件中并使用彼此的类是有问题的。该问题在Derived class defined later in the same file “does not exist”?answered by Jon中描述。