php 实现Hash表功能实例详解


Posted in PHP onNovember 29, 2016

php 实现Hash表功能

Hash表作为最重要的数据结构之一,也叫做散列表。使用PHP实现Hash表的功能。PHP可以模拟实现Hash表的增删改查。通过对key的映射到数组中的一个位置来访问。映射函数叫做Hash函数,存放记录的数组称为Hash表。

Hash函数把任意长度的和类型的key转换成固定长度输出。不同的key可能拥有相同的hash。
Hash表的时间复杂度为O(1)

<?php
class HashTable{
  private $arr = array();
  private $size = 10;
  public function __construct(){
    //SplFixedArray创建的数组比一般的Array()效率更高,因为更接近C的数组。创建时需要指定尺寸
    $this->arr = new SplFixedArray($this->size);
  }
  /**
   * Description: 简单hash算法。输入key,输出hash后的整数
   * @param $key
   * @return int
   */
  private function simpleHash($key){
    $len = strlen($key);
    //key中每个字符所对应的ASCII的值
    $asciiTotal = 0;
    for($i=0; $i<$len; $i++){
      $asciiTotal += ord($key[$i]);
    }
    return $asciiTotal % $this->size;
  }
  /**
   * Description: 赋值
   * @param $key
   * @param $value
   * @return bool
   */
  public function set($key, $value){
    $hash = $this->simpleHash($key);
    $this->arr[$hash] = $value;
    return true;
  }
  /**
   * Description: 取值
   * @param $key
   * @return mixed
   */
  public function get($key){
    $hash = $this->simpleHash($key);
    return $this->arr[$hash];
  }
  public function getList(){
    return $this->arr;
  }
  public function editSize($size){
    $this->size = $size;
    $this->arr->setSize($size);
  }
}
?>

 下面对我们的HashTable进行测试。

<?php
//测试1
$arr = new HashTable();
for($i=0; $i<15; $i++){
  $arr->set('key'.$i, 'value'.$i);
}
print_r($arr->getList());

//测试2
$arr->editSize(15);
for($i=0; $i<15; $i++){
  $arr->set('key'.$i, 'value'.$i);
}
print_r($arr->getList());
?>

 改变了值之后可以存放更多的元素。但是仍然存在不同的key可能产生相同的hash值,那么赋值的时候后操作会覆盖前操作的问题。这种冲突的问题我们来用拉链法解决。

拉链法解决冲突。拉链法解决冲突的做法是将所有的相同Hash值的key放在一个链表中,比如key3和key14在hash之后都是0,那么在数组的键为0的地方存储这两个值,形式是链表。如果不能理解我的文字,请看下面的示例,看一下打印信息就明白了。拉链法是什么,就是链表。

创建一个HashNode类,用来存储key和value的值,并且存储相同hash的另一个元素。在同一条链上,查找越后的元素越费时。时间复杂度为O(n).

<?php
class HashNode{
  public $key;
  public $value;
  public $nextNode;
  public function __construct($key, $value, $nextNode=Null){
    $this->key = $key;
    $this->value = $value;
    $this->nextNode = $nextNode;
  }
}
class NewHashTable{
  private $arr;
  private $size = 10;
  public function __construct(){
    $this->arr = new SplFixedArray($this->size);
  }
  private function simpleHash($key){
    $asciiTotal = 0;
    $len = strlen($key);
    for($i=0; $i<$len; $i++){
      $asciiTotal += ord($key[$i]);
    }
    return $asciiTotal % $this->size;
  }
  public function set($key, $value){
    $hash = $this->simpleHash($key);
    if(isset($this->arr[$hash])){
      $newNode = new HashNode($key, $value, $this->arr[$hash]);
    }else{
      $newNode = new HashNode($key, $value, null);
    }
    $this->arr[$hash] = $newNode;
    return true;
  }
  public function get($key){
    $hash = $this->simpleHash($key);
    $current = $this->arr[$hash];
    while(!empty($current)){
      if($current->key == $key){
        return $current->value;
      }
      $current = $current->nextNode;
    }
    return NULL;
  }
  public function getList(){
    return $this->arr;
  }
}
?>

对我们新的HashTable进行测试

<?php
//测试1
$newArr = new NewHashTable();
for($i=0; $i<30; $i++){
  $newArr->set('key'.$i, 'value'.$i);
}
print_r($newArr->getList());
var_dump($newArr->get('key3'));
?>

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

PHP 相关文章推荐
php抓即时股票信息
Oct 09 PHP
PHP与MySQL开发中页面乱码的产生与解决
Mar 27 PHP
应用开发中涉及到的css和php笔记分享
Aug 02 PHP
php数组函数序列之asort() - 对数组的元素值进行升序排序,保持索引关系
Nov 02 PHP
php number_format() 函数通过千位分组来格式化数字的实现代码
Aug 06 PHP
使用PHP curl模拟浏览器抓取网站信息
Oct 28 PHP
通过curl模拟post和get方式提交的表单类
Apr 23 PHP
php实现的双向队列类实例
Sep 24 PHP
php从完整文件路径中分离文件目录和文件名的方法
Mar 13 PHP
thinkPHP实现将excel导入到数据库中的方法
Apr 22 PHP
laravel5使用freetds连接sql server的方法
Dec 07 PHP
php实现商城购物车的思路和源码分析
Jul 23 PHP
php文件上传 你真的掌握了吗
Nov 28 #PHP
php微信公众号js-sdk开发应用
Nov 28 #PHP
php微信高级接口调用方法(自定义菜单接口、客服接口、二维码)
Nov 28 #PHP
php微信公众平台交互与接口详解
Nov 28 #PHP
php微信公众号开发模式详解
Nov 28 #PHP
jQuery+php简单实现全选删除的方法
Nov 28 #PHP
PHP中的use关键字及文件的加载详解
Nov 28 #PHP
You might like
PHP判断指定时间段的2个方法
2014/03/14 PHP
ThinkPHP函数详解之M方法和R方法
2015/09/10 PHP
Laravel+jQuery实现AJAX分页效果
2016/09/14 PHP
详解PHP素材图片上传、下载功能
2019/04/12 PHP
Javascript isArray 数组类型检测函数
2009/10/08 Javascript
基于jquery的鼠标拖动效果代码
2012/05/30 Javascript
jquery获取当前点击对象的value方法
2014/02/28 Javascript
JavaScript函数详解
2015/02/27 Javascript
jquery仅用6行代码实现滑动门效果
2015/09/07 Javascript
jQuery mobile转换url地址及获取url中目录部分的方法
2015/12/04 Javascript
基于javascript实现精确到毫秒的倒计时限时抢购
2016/04/17 Javascript
从零学习node.js之模块规范(一)
2017/02/21 Javascript
Webpack性能优化 DLL 用法详解
2017/08/10 Javascript
原生JS+HTML5实现跟随鼠标一起流动的粒子动画效果
2018/05/03 Javascript
JS实现的贪吃蛇游戏完整实例
2019/01/18 Javascript
前端天气插件tpwidget使用方法详解
2019/06/24 Javascript
javascript如何实现create方法
2019/11/04 Javascript
微信小程序获取当前时间及星期几的实例代码
2020/09/20 Javascript
[44:21]Ti4 循环赛第四日 附加赛NEWBEE vs LGD
2014/07/13 DOTA
python 排序算法总结及实例详解
2016/09/28 Python
pandas实现excel中的数据透视表和Vlookup函数功能代码
2020/02/14 Python
在pycharm中实现删除bookmark
2020/02/14 Python
Django:使用filter的pk进行多值查询操作
2020/07/15 Python
浅析HTML5 meta viewport参数
2020/10/28 HTML / CSS
英国著名的药妆网站:Escentual
2016/07/29 全球购物
前台接待岗位职责
2013/12/03 职场文书
外语系大学生自荐信范文
2014/03/01 职场文书
保险公司晨会主持词
2014/03/22 职场文书
村抢险救灾方案
2014/05/09 职场文书
经济信息系毕业生自荐信
2014/06/02 职场文书
2014年国庆晚会主持词
2014/09/19 职场文书
领导干部整治奢华浪费之风思想汇报
2014/10/07 职场文书
2015年校本培训工作总结
2015/07/24 职场文书
幼儿园亲子活动感想
2015/08/07 职场文书
学校2016年九九重阳节活动总结
2016/04/01 职场文书
Windows11插耳机没反应怎么办? win11耳机没声音的多种解决办法
2021/11/21 数码科技