php spl 排序,PHP SPL神器实现堆排序

之前学习过内部排序的八大算法,也一一写过代码实现。其中堆排序的原理是

将一颗二叉树初始化为堆

依次将最后一个结点与堆顶结点交换。然后调整堆顶元素位置,重置堆。

将二叉树初始化为堆可以看做从最后一个非叶子结点开始,依次调整子堆的堆顶元素,重置堆是指重置堆顶元素。

这种算法的实现如下:

#堆排序

function heapSort(&$arr) {

#初始化大顶堆

initHeap($arr);

#开始交换首尾节点,并每次减少一个末尾节点再调整堆,直到剩下一个元素

for($end = count($arr) - 1; $end >= 0; $end--) {

$temp = $arr[0];

$arr[0] = $arr[$end];

$arr[$end] = $temp;

ajustNodes($arr, 0, $end - 1);

}

}

#初始化最大堆,从最后一个非叶子节点开始,最后一个非叶子节点编号为 数组长度/2 向下取整

function initHeap(&$arr) {

$len = count($arr);

for($start = floor($len / 2) - 1; $start > 0; $start--) {

ajustNodes($arr, $start, $len - 1);

}

}

#调整节点

[email protected] $arr 待调整数组

[email protected] $start 调整的父节点坐标

[email protected] $end 待调整数组结束节点坐标

function ajustNodes(&$arr, $start, $end) {

$maxInx = $start;

$len = $end + 1; #待调整部分长度

$leftChildInx = ($start + 1) * 2 - 1; #左孩子坐标

$rightChildInx = ($start + 1) * 2; #右孩子坐标

#如果待调整部分有左孩子

if($leftChildInx + 1 <= $len) {

#获取最小节点坐标

if($arr[$maxInx] < $arr[$leftChildInx]) {

$maxInx = $leftChildInx;

}

#如果待调整部分有右子节点

if($rightChildInx + 1 <= $len) {

if($arr[$maxInx] < $arr[$rightChildInx]) {

$maxInx = $rightChildInx;

}

}

}

#交换父节点和最大节点

if($start != $maxInx) {

$temp = $arr[$start];

$arr[$start] = $arr[$maxInx];

$arr[$maxInx] = $temp;

#如果交换后的子节点还有子节点,继续调整

if(($maxInx + 1) * 2 <= $len) {

ajustNodes($arr, $maxInx, $end);

}

}

}

$arr = array(1, 5, 3, 7, 9 ,10, 2, 8);

heapSort($arr);

print_r($arr);

?>

现在学了SPL这种神器,看下如何实现堆排序:

function splHeapSort($arr){

$heap = new SplMinHeap();

//初始化小顶堆

foreach ($arr as $v){

$heap->insert($v);

}

while(!$heap->isEmpty()){

$res[] = $heap->extract();

}

return $res;

}

$arr = array(2,5,9,1,4,7,3,4,6,0,1,2,4,6,8,9,2,3);

$arr = splHeapSort($arr);

print_r($arr);

?>

什么!!!这么简单??对,就是这么简单,不要问为什么,强大,任性!

原文:http://www.cnblogs.com/taijun/p/4211515.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值