PHP实现的堆排序算法详解


Posted in PHP onAugust 17, 2017

本文实例讲述了PHP实现的堆排序算法。分享给大家供大家参考,具体如下:

经验

工作了,面试我工作这家公司时被技术面打击得不行,因为自己的数据结构等基础学得实在太差,虽然原来是想做设计师的说。。。不过看在PHP写得还凑合的份上能来实习了,但还是决心恶补一下基础。 其实自己之前也确实感觉到了基础的重要性,一些比较深的东西都比较底层,不学好根本没法进行。像我之前用PHP做websocket,就牵扯到数据包、数据帧等概念,搞不清楚,连数据都没法处理,还得后来补。所以我准备重新学一下数据结构,算法,网络等基础知识,也在此跟大家提个醒,别像我一样走反了方向,甚至到明白过来就已经晚了。

今天来说一下被问到的堆排序的问题,当时被问到时,连完全二叉树的概念都忘了。不过幸好我还有一点点数据结构基础,看了点资料也有些明白了,所以想用PHP写一下二叉树的堆排序,顺便也复习下二叉树,堆等数据结构。

堆(heap)是计算机科学中一类特殊的数据结构的统称,通常是一个可以被看做一棵树的数组对象

堆{k1,k2,ki,…,kn} (ki <= k2i,ki <= k2i+1)|(ki >= k2i,ki >= k2i+1), (i = 1,2,3,4...n/2)

关于堆:

堆中某个节点的值总是不大于或不小于其父节点的值;
堆总是一棵完全二叉树(下面)。
将根节点最大的堆叫做最大堆或大根堆,根节点最小的堆叫做最小堆或小根堆。

完全二叉树

说到堆排序,就不能不提完全二叉树,这些基本概念在网上到处都是,我摘了个最简单的。。

完全二叉树:除最后一层外,每一层上的节点数均达到最大值;在最后一层上只缺少右边的若干结点。

我自己总结认为,正是因为有下面两个特点,

1. 只允许最后一层有空缺结点且空缺在右边,即叶子结点只能在层次最大的两层上出现(存储方式的规则性);
2. 若i>1,tree的双亲为tree[i div 2](其父子结点值的规律性);

才使得其进行排序非常方便。

堆排序

堆排序求升序用大顶堆,求降序用小顶堆。

本例用求降序的小顶堆来解析。

堆排序步骤如下:

1、我们将数据(49、38、65、97、76、13、27、50)建立一个数组$arr;
2、用数组$arr建立一个小顶堆(主要步骤,会在代码注释里解释,下图是用一个数组建立小顶堆的过程);
3、将堆的根(最小的元素)与最后一个叶子交换,并将堆长度减一,跳到第二步;
4、重复2-3步,直到堆中只有一个结点,排序完成。

PHP实现的堆排序算法详解

堆排序的PHP实现

//因为是数组,下标从0开始,所以,下标为n根结点的左子结点为2n+1,右子结点为2n+2;
//初始化值,建立初始堆
$arr=array(49,38,65,97,76,13,27,50);
$arrSize=count($arr);
//将第一次排序抽出来,因为最后一次排序不需要再交换值了。
buildHeap($arr,$arrSize);
for($i=$arrSize-1;$i>0;$i--){
  swap($arr,$i,0);
  $arrSize--;
  buildHeap($arr,$arrSize);
}
//用数组建立最小堆
function buildHeap(&$arr,$arrSize){
  //计算出最开始的下标$index,如图,为数字"97"所在位置,比较每一个子树的父结点和子结点,将最小值存入父结点中
  //从$index处对一个树进行循环比较,形成最小堆
  for($index=intval($arrSize/2)-1; $index>=0; $index--){
    //如果有左节点,将其下标存进最小值$min
    if($index*2+1<$arrSize){
      $min=$index*2+1;
      //如果有右子结点,比较左右结点的大小,如果右子结点更小,将其结点的下标记录进最小值$min
      if($index*2+2<$arrSize){
        if($arr[$index*2+2]<$arr[$min]){
          $min=$index*2+2;
        }
      }
      //将子结点中较小的和父结点比较,若子结点较小,与父结点交换位置,同时更新较小
      if($arr[$min]<$arr[$index]){
        swap($arr,$min,$index);
      }
    }
  }
}
//此函数用来交换下数组$arr中下标为$one和$another的数据
function swap(&$arr,$one,$another){
  $tmp=$arr[$one];
  $arr[$one]=$arr[$another];
  $arr[$another]=$tmp;
}

下面是排序的最终结果:

PHP实现的堆排序算法详解

希望本文所述对大家PHP程序设计有所帮助。

PHP 相关文章推荐
一篇有意思的技术文章php介绍篇
Oct 26 PHP
php缩放图片(根据宽高的等比例缩放)实例介绍
Jun 09 PHP
基于PHP的简单采集数据入库程序
Jul 30 PHP
四种php中webservice实现的简单架构方法及实例
Feb 03 PHP
使用PHP生成图片的缩略图的方法
Aug 18 PHP
PHP简单实现断点续传下载的方法
Sep 25 PHP
WIFI万能钥匙密码查询接口实例
Sep 28 PHP
yii的入口文件index.php中为什么会有这两句
Aug 04 PHP
php实现构建排除当前元素的乘积数组方法
Oct 06 PHP
php5对象复制、clone、浅复制与深复制实例详解
Aug 14 PHP
php+iframe 实现上传文件功能示例
Mar 04 PHP
PHP 技巧 * SVG 保存为图片(分享图生成)
Apr 02 PHP
基于php编程规范(详解)
Aug 17 #PHP
PHP数据库操作四:mongodb用法分析
Aug 16 #PHP
PHP Laravel 上传图片、文件等类封装
Aug 16 #PHP
PHP数据库操作三:redis用法分析
Aug 16 #PHP
PHP数据库操作二:memcache用法分析
Aug 16 #PHP
PHP数据库编程之MySQL优化策略概述
Aug 16 #PHP
PHP回调函数与匿名函数实例详解
Aug 16 #PHP
You might like
PHP 彩色文字实现代码
2009/06/29 PHP
PHP中开发XML应用程序之基础篇 添加节点 删除节点 查询节点 查询节
2010/07/09 PHP
php上传文件,创建递归目录的实例代码
2013/10/18 PHP
可兼容php5与php7的cURL文件上传功能实例分析
2018/05/11 PHP
重写javascript中window.confirm的行为
2012/10/21 Javascript
原生js实现给指定元素的后面追加内容
2013/04/10 Javascript
js实现连续英文字符自动换行兼容ie6 ie7和firefox
2013/09/06 Javascript
Node.js文件操作详解
2014/08/16 Javascript
JS实现在线统计一个页面内鼠标点击次数的方法
2015/02/28 Javascript
浅析JavaScript中作用域和作用域链
2016/12/06 Javascript
canvas知识总结
2017/01/25 Javascript
vue拦截器Vue.http.interceptors.push使用详解
2017/04/22 Javascript
Vue2.0实现购物车功能
2017/06/05 Javascript
nodejs后台集成ueditor富文本编辑器的实例
2017/07/11 NodeJs
Nodejs下使用gm圆形裁剪并合成图片的示例
2018/02/22 NodeJs
Webpack之tree-starking 解析
2018/09/11 Javascript
Echarts之悬浮框中的数据排序问题
2018/11/08 Javascript
微信小程序自定义组件传值 页面和组件相互传数据操作示例
2019/05/05 Javascript
手把手教你 CKEDITOR 4 扩展插件制作
2019/06/18 Javascript
分享一款超好用的JavaScript 打包压缩工具
2020/04/26 Javascript
[54:45]2018DOTA2亚洲邀请赛 4.1 小组赛 A组 Optic vs OG
2018/04/02 DOTA
Python获取当前时间的方法
2014/01/14 Python
Python内置函数的用法实例教程
2014/09/08 Python
matplotlib作图添加表格实例代码
2018/01/23 Python
Python实现的矩阵转置与矩阵相乘运算示例
2019/03/26 Python
Python参数解析模块sys、getopt、argparse使用与对比分析
2019/04/02 Python
python输入多行字符串的方法总结
2019/07/02 Python
tensorflow tf.train.batch之数据批量读取方式
2020/01/20 Python
pycharm通过ssh连接远程服务器教程
2020/02/12 Python
python实现3D地图可视化
2020/03/25 Python
你不知道的葡萄干处理法、橙蜜处理法、二氧化碳酵母法
2021/03/17 冲泡冲煮
世界上最大的巴士旅游观光公司:Big Bus Tours
2016/10/20 全球购物
加拿大著名的奢侈品购物网站:SSENSE(支持中文)
2020/06/25 全球购物
MySQL面试题目集锦
2016/04/14 面试题
老师对学生的寄语
2014/04/09 职场文书
党性修养心得体会2016
2016/01/21 职场文书