php - 何时调用 SplHeap::isCorrupted?
问题描述
抽象类SplHeap
提供了isCorrupted方法:
判断堆是否处于损坏状态
public SplHeap::isCorrupted ( void ) : bool
我想知道这种方法如何有用,更不用说堆如何损坏了。人们会期望内部堆实现是可靠的,并且永远不会被破坏。
起初我认为也许可以直接访问底层数组,这将允许这样的事情(类似于 Python 的heapq
实现可能发生的事情):
$heap = new SplMinHeap();
$heap->insert(9);
$heap->insert(5);
echo $heap->top(); // 5
$heap[0] = 10; // make the heap inconsistent? -- not possible
堆的内部数据结构原来是私有的。上述堆的A var_dump
,呈现如下:
object(SplMinHeap)#1 (3) {
["flags":"SplHeap":private]=>int(0)
["isCorrupted":"SplHeap":private]=>bool(false)
["heap":"SplHeap":private]=>array(2) {
[0]=>int(5)
[1]=>int(9)
}
}
作为另一种可能性,我认为内存约束可能会导致堆损坏,但在这种情况下,让任何修改方法(insert
, extract
, ...)引发异常并将堆保持在原始状态似乎更有用.
所以我的问题是:为什么我们需要调用$heap->isCorrupted()
,它会在哪种情况下返回true
?
解决方案
compare
当用户定义的函数中发生异常时,堆可能会损坏。SplHeap::compare上的文档有以下内容:
警告抛出异常
SplHeap::compare()
会破坏堆并将其置于阻塞状态。您可以通过调用取消阻止它SplHeap::recoverFromCorruption()
。但是,某些元素可能未正确放置,因此可能会破坏堆属性。
例如,这个脚本会产生一个损坏的堆:
final class MySplHeap extends SplHeap {
protected function compare($a, $b) {
echo "compare $a with $b\n"; // Useful to see what is happening...
if ($a === $b) return 0;
if ($a > $b) return 1;
throw new Exception("my error");
}
}
$heap = new MySplHeap();
try {
$heap->insert(3);
$heap->insert(2);
$heap->insert(1);
$heap->insert(4); // compare method raises error here
} catch(Exception $e) {}
var_dump($heap->isCorrupted()); // bool(true)
echo $heap->extract(); // RuntimeException: Heap is corrupted, heap properties are no longer ensured.
由于错误,无法将值 4 放置在堆中的正确位置。
显而易见的补救措施是确保比较函数中没有异常发生。
推荐阅读
- python - 输入数据框不是熊猫数据框
- reactjs - 反应路由器:路径='/'的路由不起作用
- html - 如何将图像放在一个部分中?
- html - 当其他元素居中对齐时,使用 Flexbox 将页脚与页面底部对齐
- ios - 具有谓词核心数据搜索的泛型方法不会返回正确的结果
- wordpress - 如何在 WooCommerce 中获得最畅销的产品类别 ID?
- kivy - kivymd 屏幕在收听麦克风之前未更新
- node.js - Node.js 'ws' 和 Redis PUB/SUB 的性能推荐,用于基于房间的实时通信
- android - Jetpack Compose Crossfade 在 Alpha 中损坏
- crud - 为什么 body-parser 在我的 VSCode 中通过一行来敲击以及如何让它发挥作用?