PHP字典树(Trie树)定义与实现方法示例


Posted in PHP onOctober 09, 2017

本文实例讲述了PHP字典树(Trie树)定义与实现方法。分享给大家供大家参考,具体如下:

Trie树的概念(百度的解释):字典树又称单词查找树,Trie树,是一种树形结构,是一种哈希树的变种。典型应用是用于统计,排序和保存大量的字符串(但不仅限于字符串),所以经常被搜索引擎系统用于文本词频统计。它的优点是:利用字符串的公共前缀来减少查询时间,最大限度地减少无谓的字符串比较,查询效率比哈希树高。

我的理解是用来做字符串搜索的,每个节点只包含一个字符,比如录入单词"world",则树的结构是:

PHP字典树(Trie树)定义与实现方法示例

这时再录入单词"worab",则树的结构为:

PHP字典树(Trie树)定义与实现方法示例

所以每个节点必须还要一个字段is_end标识是否为结束单词。比如用户输入wor,搜索所有wor开头的单词,假设现在有一个单词就是wor,从"w"开始检索,当检索到"r"的时候需要判断"r"节点的is_end为true,则把wor加入到结果列表,然后继续往下面检索。

PHP实现代码:

<?php
class Node{
  public $value;         // 节点值
  public $is_end = false;    // 是否为结束--是否为某个单词的结束节点
  public $childNode = array();  // 子节点
  /* 添加孩子节点--注意:可以不为引用函数,因为PHP对象赋值本身就是引用赋值 */
  public function &addChildNode($value, $is_end = false){
    $node = $this->searchChildNode($value);
    if(empty($node)){
      // 不存在节点,添加为子节点
      $node = new Node();
      $node->value = $value;
      $this->childNode[] = $node;
    }
    $node->is_end = $is_end;
    return $node;
  }
  /* 查询子节点 */
  public function searchChildNode($value){
    foreach ($this->childNode as $k => $v) {
      if($v->value == $value){
        // 存在节点,返回该节点
        return $this->childNode[$k];
      }
    }
    return false;
  }
}
/* 添加字符串 */
function addString(&$head, $str){
  $node = null;
  for ($i=0; $i < strlen($str); $i++) {
    if($str[$i] != ' '){
      $is_end = $i != (strlen($str) - 1) ? false : true;
      if($i == 0){
        $node = $head->addChildNode($str[$i], $is_end);
      }else{
        $node = $node->addChildNode($str[$i], $is_end);
      }
    }
  }
}
/* 获取所有字符串--递归 */
function getChildString($node, $str_array = array(), $str = ''){
  if($node->is_end == true){
    $str_array[] = $str;
  }
  if(empty($node->childNode)){
    return $str_array;
  }else{
    foreach ($node->childNode as $k => $v) {
      $str_array = getChildString($v, $str_array, $str . $v->value);
    }
    return $str_array;
  }
}
/* 搜索 */
function searchString($node, $str){
  for ($i=0; $i < strlen($str); $i++) {
    if($str[$i] != ' '){
      $node = $node->searchChildNode($str[$i]);
      // print_r($node);
      if(empty($node)){
        // 不存在返回空
        return false;
      }
    }
  }
  return getChildString($node);
}
/* 调用测试开始 */
$head = new Node;  // 树的head
// 添加单词
addString($head, 'hewol');
addString($head, 'hemy');
addString($head, 'heml');
addString($head, 'you');
addString($head, 'yo');
// 获取所有单词
$str_array = getChildString($head);
// 搜索
$search_array = searchString($head, 'hem');
// 循环打印所有搜索结果
foreach ($search_array as $key => $value) {
  echo 'hem' . $value . '<br>'; // 输出带上搜索前缀
}

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

PHP 相关文章推荐
php+oracle 分页类
Oct 09 PHP
cmd下运行php脚本
Nov 25 PHP
PHP无限分类(树形类)的深入分析
Jun 02 PHP
dedecms函数分享之获取某一栏目所有子栏目
May 19 PHP
CodeIgniter中使用cookie的三种方式详解
Jul 18 PHP
yii实现创建验证码实例解析
Jul 31 PHP
destoon实现会员商铺中指定会员或会员组投放广告的方法
Aug 21 PHP
php自定文件保存session的方法
Dec 10 PHP
php生成RSS订阅的方法
Feb 13 PHP
Yii2框架实现数据库常用操作总结
Feb 08 PHP
PHP魔术方法之__call与__callStatic使用方法
Jul 23 PHP
PHP异步进程助手async-helper
Feb 05 PHP
PHP完全二叉树定义与实现方法示例
Oct 09 #PHP
PHP实现的折半查询算法示例
Oct 09 #PHP
PHP实现的MD5结合RSA签名算法实例
Oct 07 #PHP
PHP实现的mysql操作类【MySQL与MySQLi方式】
Oct 07 #PHP
PHP实现打包下载文件的方法示例
Oct 07 #PHP
PHP基于PDO调用sqlserver存储过程通用方法【基于Yii框架】
Oct 07 #PHP
PHP使用PDO调用mssql存储过程的方法示例
Oct 07 #PHP
You might like
PHP中多维数组的foreach遍历示例
2014/06/13 PHP
php版微信公众号自定义分享内容实现方法
2016/09/22 PHP
Jquery 扩展方法
2010/05/06 Javascript
jQuery.Validate 使用笔记(jQuery Validation范例 )
2010/06/25 Javascript
基于Jquery的仿Windows Aero弹出窗(漂亮的关闭按钮)
2010/09/28 Javascript
基于jquery完美拖拽,可返回拖动轨迹
2012/03/29 Javascript
jQuery 联动日历实现代码
2012/05/31 Javascript
jquery实现简单的拖拽效果实例兼容所有主流浏览器(优化篇)
2013/06/28 Javascript
JavaScript显示当然日期和时间即年月日星期和时间
2013/10/29 Javascript
js中的cookie的读写操作示例详解
2014/04/17 Javascript
JavaScript DOM元素尺寸和位置
2015/04/13 Javascript
javascript中SetInterval与setTimeout的定时器用法
2015/08/24 Javascript
谈谈javascript中使用连等赋值操作带来的问题
2015/11/26 Javascript
在 Express 中使用模板引擎
2015/12/10 Javascript
BootStrap iCheck插件全选与获取value值的解决方法
2016/08/24 Javascript
原生js开发的日历插件
2017/02/04 Javascript
ionic3实战教程之随机布局瀑布流的实现方法
2017/12/28 Javascript
详解vue移动端项目的适配(以mint-ui为例)
2018/08/17 Javascript
详解vue 不同环境配置不同的打包命令
2019/04/07 Javascript
Vue实现移动端拖拽交换位置
2020/07/29 Javascript
js+canvas实现转盘效果(两个版本)
2020/09/13 Javascript
[01:02:47]EG vs Secret 2019国际邀请赛淘汰赛 胜者组 BO3 第一场 8.21.mp4
2020/07/19 DOTA
用Python实现一个简单的线程池
2015/04/07 Python
Python 序列的方法总结
2016/10/18 Python
python虚拟环境的安装配置图文教程
2017/10/20 Python
pytorch: tensor类型的构建与相互转换实例
2018/07/26 Python
在win64上使用bypy进行百度网盘文件上传功能
2020/01/02 Python
pytorch 修改预训练model实例
2020/01/18 Python
舒适的豪华鞋:Taryn Rose
2018/05/03 全球购物
日本乐天德国站:Rakuten.de
2019/05/16 全球购物
俄罗斯连接商品和买家的在线平台:goods.ru
2020/11/30 全球购物
环保建议书
2014/03/12 职场文书
优秀少先队辅导员先进事迹材料
2014/05/18 职场文书
年会邀请函范文
2015/01/30 职场文书
会议邀请函
2015/01/30 职场文书
写自招自荐信的绝招!
2019/04/19 职场文书