JavaScript队列、优先队列与循环队列


Posted in Javascript onNovember 14, 2016

队列是一种遵从先进先出(FIFO)原则的有序集合
队列在尾部添加新元素,从顶部移除元素

队列的理解

队列在我们生活中最常见的场景就是排队了
队列这个名字也已经很通俗易懂了

JavaScript队列、优先队列与循环队列

和栈很像,这不过队列是先入先出的数据结构

JavaScript队列、优先队列与循环队列

队列的前面是队头
队列的后面是队尾
出队从队头出
入队从队尾入

队列的创建

和栈类似,这里我就不就不??铝
同样需要实现一些功能
这里我类比生活中的排队上厕所

  • 向队列中添加元素(进入排队的队伍中)
  • 移除队头元素(队伍最前面的人出队进入厕所)
  • 查看队头元素(查看队伍最前面的人)
  • 判断队列是否为空(看看队伍中有没有人)
  • 移除队伍全部元素(厕所炸了,都散了吧)
  • 查看栈里元素个数(查看排队的有多少人)

于是我们可以创建一个完整队列实现,同样是利用我们的数组实现
数组头就是队列头

function Queue() {
  var items = [];
  this.enqueue = function (ele) {
    items.push(ele);
  };//入队
  this.dequeue = function () {
    return items.shift();
  };//出队
  this.front = function () {
    return items[0];
  };//查看队头元素
  this.isEmpty = function () {
    return items.length === 0;
  };//判断队列是否为空
  this.size = function () {
    return items.length;
  };//队列大小
  this.clear = function () {
    items = [];
  };//清空队列
  this.print = function () {
    console.log(items.toString());
  };//打印队列
}
var queue = new Queue(); //声明队列的实例

队列的使用

下面我们就用这个队列简单模拟排队

var queue = new Queue();
console.log("队列是否为空: " + queue.isEmpty());
queue.enqueue('Mr.A');
queue.enqueue('Mr.B');
queue.enqueue('Mr.C');
console.log("当前队列:");
queue.print();
console.log("出队的人: " + queue.dequeue());
console.log("当前队列:");
queue.print();

控制台打印:

JavaScript队列、优先队列与循环队列

优先队列

在我们排队上厕所的时候,来了一位拥有VIP会员卡的朋友,插到了队伍的最前面
过了一会儿又来了一位拥有SVIP会员卡的朋友,插到了VIP的前面

虽然这个比喻可能不恰当,但是生活中可能存在有优先级的队列
优先级高的人可以查到优先级低的人前面

这就是循环队列

如果优先值小的元素放到队列的前面,这叫做最小优先队列
反之优先值大的元素放到队列的前面,这叫做最大优先队列
但其实他们两个仅仅是一个判断的改变,实现方式是一样的
优先队列较普通队列的区别也就是入队要判断优先级,并且需要对我们的元素进行处理,其他方法不变
这处理也就是把元素包装为一个拥有优先级的对象
既然所有对象都有着同样的属性,那我们毫无疑问就应该使用工厂构建
我们可以稍微修改一下我们的队列类
来实现一个最小优先队列

function PriorityQueue() {
  var items = [];
  function QueEle(ele, priority){ //封装我们的元素为一个对象
    this.ele = ele; //元素
    this.priority = priority; //优先级
  }
  this.enqueue = function (ele, priority) {
    var queObj = new QueEle(ele, priority); //创建队列元素对象
    if(this.isEmpty()){ //如果队列是空的,直接插入
      this.push(queObj);
    }else{
      var bAdded = false;
      for(var i = 0, len = items.length; i < len; i++){ 
        if(priority < items[i].priority){
          items.splice(i, 0, queObj); // 循环队列,如果优先级小于这个位置元素的优先级,插入
          bAdded = true;
          break;
        }
      }
      if(!bAdded){
        items.push(queObj); // 如果循环一圈都没有找到能插队的位置,直接插入队列尾部
      }
    }
  };
  this.dequeue = function () {
    return items.shift();
  };
  this.front = function () {
    return items[0];
  };
  this.isEmpty = function () {
    return items.length === 0;
  };
  this.size = function () {
    return items.length;
  };
  this.clear = function () {
    items = [];
  };
  this.print = function () {
    //这个地方稍微修改一下下
    var temp = [];
    for(var i = 0, len = items.length; i < len; i++){
      temp.push(items[i].ele);
    }
    console.log(temp.toString());
  };
}

解释我已经在代码里说的很明白
下面我们就用这个优先队列同样来模拟排队上WC

var pQueue = new PriorityQueue();
pQueue.enqueue('Mr.A', 3);
pQueue.enqueue('Mr.B', 3);
pQueue.enqueue('Mr.C', 3);
console.log("原队列:");
pQueue.print();
pQueue.enqueue('VIP', 2);
pQueue.enqueue('SVIP', 1);
console.log("新队列:");
pQueue.print();

控制台打印:

JavaScript队列、优先队列与循环队列

循环队列

循环队列典型的例子击鼓传花
还记得在我上高中的时候我们晚自习一停电就玩这个
拿一个东西当“花”,轮着传,“鼓”一停,拿到花的同学就要站起来唱歌
可以把循环队列当作是队列的应用
下面我们来模拟实现循环队列击鼓传花

function hotPotato(pepoleList, frequency){ //参数:表示人的数组,传花的频率
  var queue = new Queue();
  for(var i = 0, len = pepoleList.length; i < len; i++){
    queue.enqueue(pepoleList[i]); //初始化,进入队列
  }
  var eliminated;//被淘汰的同学
  while(queue.size() > 1){ //只要队列至少还有两个人,就一直循环
    for(var i = 0; i < frequency; i++){//出队入队,模拟循环效果
      queue.enqueue(queue.dequeue());
    }
    eliminated = queue.dequeue();//清算
    console.log(eliminated + '被淘汰');
  }
  return queue.dequeue();//返回队列中的最后一人
}
var pepole = ['Mr.A','Mr.B','Mr.C','Mr.D','Mr.E','Mr.F'];
var gameWinner = hotPotato(pepole, 12);
console.log('全场最佳:' + gameWinner);

控制台输出:

 JavaScript队列、优先队列与循环队列

以上就是JavaScript下的队列实现。
我们还简单理解了两个特殊的队列:优先队列与循环队列。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JS 控制非法字符的输入代码
Dec 04 Javascript
Javascript 面向对象 对象(Object)
May 13 Javascript
jQuery中jqGrid分页实现代码
Nov 04 Javascript
简单几行JS Code实现IE邮件转发新浪微博
Jul 03 Javascript
JavaScript Split()方法
Dec 18 Javascript
微信小程序 页面跳转传值实现代码
Jul 27 Javascript
vue中路由验证和相应拦截的使用详解
Dec 13 Javascript
AngularJS select加载数据选中默认值的方法
Feb 28 Javascript
Vue项目分环境打包的实现步骤
Apr 02 Javascript
详解webpack 打包文件体积过大解决方案(code splitting)
Apr 10 Javascript
node-red File读取好保存实例讲解
Sep 11 Javascript
微信小程序点击item使之滚动到屏幕中间位置
Mar 25 Javascript
JavaScript中setTimeout的那些事儿
Nov 14 #Javascript
jquery css实现邮箱自动补全
Nov 14 #Javascript
JS常用算法实现代码
Nov 14 #Javascript
node.js缺少mysql模块运行报错的解决方法
Nov 13 #Javascript
JavaScript判断浏览器对CSS3属性是否支持的多种方法
Nov 13 #Javascript
JS实现的几个常用算法
Nov 12 #Javascript
AngularJS操作键值对象类似java的hashmap(填坑小结)
Nov 12 #Javascript
You might like
php实现用户登陆简单实例
2017/04/04 PHP
PHP读取Excel类文件
2017/05/15 PHP
PHP命名空间定义与用法实例分析
2019/08/14 PHP
最新优化收藏到网摘代码(digg,diigo)
2007/02/07 Javascript
基于JQuery实现CheckBox全选全不选
2011/06/27 Javascript
jQuery提交多个表单的小技巧
2014/07/27 Javascript
IE6兼容透明背景图片及解决方案
2015/08/19 Javascript
基于RequireJS和JQuery的模块化编程日常问题解析
2016/04/14 Javascript
基于JavaScript实现树形下拉框
2016/08/10 Javascript
bootstrap table小案例
2016/10/21 Javascript
require、backbone等重构手机图片查看器
2016/11/17 Javascript
JavaScript面向对象精要(上部)
2017/09/12 Javascript
javascript中的隐式调用
2018/02/10 Javascript
使用Angular CLI生成 Angular 5项目教程详解
2018/03/18 Javascript
extract-text-webpack-plugin用法详解
2019/02/14 Javascript
Element-ui自定义table表头、修改列标题样式、添加tooltip、:render-header使用
2019/04/11 Javascript
ionic4+angular7+cordova上传图片功能的实例代码
2019/06/19 Javascript
记录vue做微信自定义分享的一些问题
2019/09/12 Javascript
Vue实现手机号、验证码登录(60s禁用倒计时)
2020/12/19 Vue.js
[02:36]DOTA2英雄基础教程 一击致命幻影刺客
2013/12/06 DOTA
[06:49]2018DOTA2国际邀请赛寻真——VirtusPro傲视群雄
2018/08/12 DOTA
Python序列化基础知识(json/pickle)
2017/10/19 Python
详解PyCharm配置Anaconda的艰难心路历程
2018/08/13 Python
深入解析Python小白学习【操作列表】
2019/03/23 Python
Windows下pycharm创建Django 项目(虚拟环境)过程解析
2019/09/16 Python
在Pytorch中计算卷积方法的区别详解(conv2d的区别)
2020/01/03 Python
python中 _、__、__xx__()区别及使用场景
2020/06/30 Python
python利用paramiko实现交换机巡检的示例
2020/09/22 Python
Python tkinter实现日期选择器
2021/02/22 Python
美国新兴城市生活方式零售商:VILLA
2017/12/06 全球购物
德国领先的大尺码和超大尺码男装在线零售商:Bigtex
2019/06/22 全球购物
印度尼西亚最完整和最大的在线药房网站:Farmaku.com
2019/11/23 全球购物
财会专业毕业生自荐信
2014/07/09 职场文书
简单了解 MySQL 中相关的锁
2021/05/25 MySQL
vue-cli3.0修改打包后的文件名和文件地址,打包后本地运行报错解决
2022/04/06 Vue.js
python实现学生信息管理系统(面向对象)
2022/06/05 Python