今天,我们要讲的是数据结构与算法中的栈。

栈的简介

栈是什么?栈是一个后进先出(LIFO)的数据结构。栈有啥作用?栈可以模拟算法或生活中的一些后进先出的场景,比如:

  • 十进制转二进制,你需要将余数倒序输出。
  • 二叉树的先中后序非递归遍历都用到了栈。
  • 在生活中,栈可以模拟煤炉与蜂窝煤等场景。

用 JavaScript 写一个栈类

对于 JavaScript 工程师来说,没必要在开发中实现一个栈。因为 JavaScript 的内置对象 Array 已经实现了栈的相关方法。不过,好的程序员不能光用别人设计好的方法,而不理解为啥这么设计,所以我们还是自己设计一个栈玩玩吧!

我们使用构造器函数来模拟类,不了解构造器函数的同学可以看《在 JavaScript 中使用构造器函数模拟类》这篇博客。

function Stack(){
  ...
}

module.exports = Stack;

私有变量

栈类的私有变量是个数组 items,用于记录栈的元素。栈类实例化生成的对象不能直接操作 items,因为 items 在函数外面是不可见的,你只能通过一些类方法沿着作用域链来间接操作 items。

function Stack() {
  // 私有变量 items,用于记录数组,对象不能直接操作
  var items = [];
}

实现 push 、pop和 toString 方法

实现 push 、pop 和 toString 方法,跑通如下测试:

// 实例化一个 stack 对象
var stack = new Stack();
stack.push(5);
stack.push(8);

// 期望 stack 转化成的字符串为'5,8'
expect(stack.toString()).toBe('5,8');

// 期望 stack 删除并返回的是8
expect(stack.pop()).toBe(8);
// 期望 stack 转化成的字符串为'5'
expect(stack.toString()).toBe('5');

单元测试有时候就是可以作为需求文档来用的,在测试驱动开发(TDD),往往都是先写测试,再写代码。本教程用了 Jest 来进行单元测试,如果你不了解 Jest 和单元测试,可以先看《Jest 单元测试入门》这篇博客。

push 、pop 和 toString 方法 与 Array 自带的 push 、pop 和 toString 方法一样,所以实现代码如下:

function Stack() {
  // 私有变量 items,用于记录数组,对象不能直接操作
  var items = [];

  // 类方法 push,在数组末尾添加项,对象可以直接调用
  this.push = function (element) {
    items.push(element);
  };

  // 删除并返回数组末尾的项
  this.pop = function () {
    return items.pop();
  };

  // 将数组转为字符串并返回
  this.toString = function () {
    return items.toString();
  };
}

实现 peek 、isEmpty、clear、size 方法

实现 peek 、isEmpty、clear、size 方法,跑通如下测试:

// 实例化一个 stack 对象
var stack = new Stack();
stack.push(5);
stack.push(8);

// 期望 stack 最后一项是8
expect(stack.peek()).toBe(8);
// 期望 stack 的长度为2
expect(stack.size()).toBe(2);
// 期望 stack 不为空
expect(stack.isEmpty()).toBeFalsy();

stack.clear();
// 期望 stack 长度为0
expect(stack.size()).toBe(0);

上述方法比较简单,直接上代码:

function Stack() {
  // 私有变量 items,用于记录数组,对象不能直接操作
  var items = [];

  // 查看数组最后一项
  this.peek = function () {
    return items[items.length - 1];
  };
  // 判断数组是否为空
  this.isEmpty = function () {
    return items.length == 0;
  };
  // 清空数组
  this.clear = function () {
    items = [];
  };
  // 返回数组长度
  this.size = function () {
    return items.length;
  };
}

至此,栈的编写就完成了。

教程示例代码及目录

示例代码:https://github.com/lewis617/javascript-datastructures-algorithms

目录:http://www.liuyiqi.cn/tags/数据结构与算法/

JavaScript 版数据结构与算法(一)栈的更多相关文章

  1. JavaScript 版数据结构与算法(二)队列

    今天,我们要讲的是数据结构与算法中的队列. 队列简介 队列是什么?队列是一种先进先出(FIFO)的数据结构.队列有什么用呢?队列通常用来描述算法或生活中的一些先进先出的场景,比如: 在图的广度优先遍历 ...

  2. JavaScript 版数据结构与算法(三)链表

    今天,我们要讲的是数据结构与算法中的链表. 链表简介 链表是什么?链表是一种动态的数据结构,这意味着我们可以任意增删元素,它会按需扩容.为何要使用链表?下面列举一些链表的用途: 因为数组的存储有缺陷: ...

  3. JavaScript 版数据结构与算法(四)集合

    今天,我们要讲的是数据结构与算法中的集合. 集合简介 什么是集合?与栈.队列.链表这些顺序数据结构不同,集合是一种无序且唯一的数据结构.集合有什么用?在 Python 中,我经常使用集合来给数组去重: ...

  4. javascript实现数据结构与算法系列:栈 -- 顺序存储表示和链式表示及示例

    栈(Stack)是限定仅在表尾进行插入或删除操作的线性表.表尾为栈顶(top),表头为栈底(bottom),不含元素的空表为空栈. 栈又称为后进先出(last in first out)的线性表. 堆 ...

  5. JavaScript版EAN码校验算法

      <script type="text/javascript"> $(document).ready(function () { $("#btnCalc&q ...

  6. JavaScript数据结构与算法(一) 栈的实现

    TypeScript版本源码 class Stack { items = []; public push(element) { this.items.push(element); } public p ...

  7. 第一章:javascript: 数据结构与算法

    在前端工程师中,常常有一种声音,我们为什么要学数据结构与算法,没有数据结构与算法,我们一样很好的完成工作.实际上,算法是一个宽泛的概念,我们写的任何程序都可以称为算法,甚至往冰箱里放大象,也要通过开门 ...

  8. 【Java数据结构学习笔记之二】Java数据结构与算法之栈(Stack)实现

      本篇是java数据结构与算法的第2篇,从本篇开始我们将来了解栈的设计与实现,以下是本篇的相关知识点: 栈的抽象数据类型 顺序栈的设计与实现 链式栈的设计与实现 栈的应用 栈的抽象数据类型   栈是 ...

  9. java数据结构与算法之栈(Stack)设计与实现

    本篇是java数据结构与算法的第4篇,从本篇开始我们将来了解栈的设计与实现,以下是本篇的相关知识点: 栈的抽象数据类型 顺序栈的设计与实现 链式栈的设计与实现 栈的应用 栈的抽象数据类型 栈是一种用于 ...

随机推荐

  1. jdk不同版本对String拼接的优化分析

    1. 测试demo代码 测试循环中字符串拼接优化 public class ForTest { public static void main(String[] args) { String a = ...

  2. C#将Excel数据表导入SQL数据库的两种方法(转)

    最近用写个winform程序想用excel 文件导入数据库中,网上寻求办法,找到了这个经过尝试可以使用. 方法一: 实现在c#中可高效的将excel数据导入到sqlserver数据库中,很多人通过循环 ...

  3. 附录:MySQL忘记root密码

    中小型规模网站集群架构:MySQL忘记root密码 : 矮哥linux运维群:93324526 前言 你忘记系统root密码的时候,你怎么解决的? 不就是single用户进行修改密码吗?这里原理是类似 ...

  4. 浏览器console的用法

    Leo_wlCnBlogs 自由.创新.研究.探索 Linux/Windows Mono/DotNet [ Open Source .NET Development/ 使用开源工具进行DotNet软件 ...

  5. 看懂c/c++ 函数、指针、数组定义

    读懂 函数 + 指针 + 数组 c语言运算符机器优先级,看这里 结合运算符优先级,我们试着读懂函数和指针 优先级简单看 表达式提升():一级优先 函数():二级优先 数组[]:二级优先 指针定义*:三 ...

  6. 【2017集美大学1412软工实践_助教博客】团队作业9——测试与发布(Beta版本)

    题目 团队作业9--测试与发布(Beta版本)(http://www.cnblogs.com/happyzm/p/6917253.html) 团队作业9-1 测试与发布成绩 分值 1 0.5 0.5 ...

  7. 团队作业10——beta阶段项目复审

    小组的名字和链接 优点 缺点(bug报告) 最终名次 拖鞋大队 基本功能都实现了,符合用户的需求:每次都能按时完成博客,满足题目要求,所以作业完成的也比较优秀.较alpha版本新增了查重自定义的功能, ...

  8. 团队作业8——第二次项目冲刺(Beta阶段)Day1--5.18

    1.展开站立式会议: 会议内容:①团队里的新成员做简单的自我介绍. ②讨论每天的任务分配问题. ③提出一个严格要求:博客一定要及时发布,并及时提交作业,遇到困难可以提出来一起解决. ④就现阶段的项目进 ...

  9. 201521123070 《JAVA程序设计》第6周学习总结

    1. 本章学习总结 1.1 面向对象学习暂告一段落,请使用思维导图,以封装.继承.多态为核心概念画一张思维导图,对面向对象思想进行一个总结. 注1:关键词与内容不求多,但概念之间的联系要清晰,内容覆盖 ...

  10. 201521123045 《JAVA程序设计》第1周学习总结 1

    1. 本周学习总结 学习了入门的java知识,知道了jdk.eclipse等基础软件,了解了如何编译最基础的java程序.知道了java的基本原理以及java的几种数据类型.掌握使用简单编译器编写ja ...