具体细节信息
首先,"平等的定义"在我的情况下 - 当对象具有相同的结构和该结构的值时,它们是相等的。但是,它们可能不是同一个实例,或者属性可能不相同" order" (我的意思是,因为他们被分配/定义)。这里有类似的问题,如this - 但它们并没有涵盖我的案例。
由于我的代码测试目的,我需要比较PHP中的实体 - 这些实体可能是任何东西。特别是,它们可能是物体。但是,Objects comparison不安全"。想象一下,你正在比较:
$result = $objectX == $objectY;
如果对象具有循环引用,则可能导致致命错误。我准备了here的简单示例。正如我们所看到的,PHP试图遵循嵌套级别并在无限循环中失败 - 因为自然对象在内容上是相同的,但具有循环引用。
重要的细节是对象可能包含不可序列化的东西(如闭包),这使得无法依赖" seralize / unserialize"方法(即使忘记无序比较)
当前方法
我有像this这样的代码(在这里直接粘贴太多了,但以防万一,这里是gist) - 所以我在那里执行DFS并抓住情况有这样的循环参考。正如你所看到的,它非常复杂 - 顺便说一句,它很慢。
当前方法的另一个问题是 - 当对象内部有数组时,它们将在元素顺序方面进行比较,在某些情况下,这对我来说并不合适(理想情况 - 当我成为时)能够切换顺序比较),但为了克服它原生,我可能需要"排序"数组以某种方式 - 我不知道如何做到这一点 - 再次,这些数组元素的比较将是不安全的。
而且,循环数组引用也会导致失败:
$array = ['foo', $object, &$array];
问题
解决问题的其他(更好)方法可能是什么?序列化对象可能就是这种情况,但由于非有序的属性集,它将失败。
答案 0 :(得分:1)
你知道Doctrine \ Common \ Util \ Debug :: export($ class,$ maxDepth)吗?
该方法“导出”会阻止您进行无限循环并返回一个可用于制作差异的数组。
超过一定深度,没有必要走得更远 使用$ maxDepth,您可以指定比较的“准确性”。