JavaScript实现栈结构(Stack)

JavaScript实现栈结构(Stack)

一、前言

1.1.什么是数据结构?

数据结构就是在计算机中,存储和组织数据的方式。

例如:图书管理,怎样摆放图书才能既能放很多书,也方便取?

主要需要考虑两个问题:

  • 操作一:新书怎么插入?
  • 操作二:怎么找到某本指定的书?

常见的数据结构:

  • 数组(Aarray)
  • (Stack)
  • 链表(Linked List)
  • (Graph)
  • 散列表(Hash)
  • 队列(Queue)
  • (Tree)
  • (Heap)

注意:数据结构与算法与语言无关,常见的编程语言都有直接或间接的使用上述常见的数据结构。

1.2.什么是算法?

算法(Algorithm)的定义

  • 一个有限指令集,每条指令的描述不依赖于语言;
  • 接收一些输入(有些情况下不需要输入);
  • 产生输入;
  • 一定在有限步骤之后终止;

算法通俗理解:解决问题的办法/步骤逻辑。数据结构的实现,离不开算法。

二、栈结构(Stack)

2.1.简介

数组是一个线性结构,并且可以在数组的任意位置插入和删除元素。而栈和队列就是比较常见的受限的线性结构。如下图所示:

栈的特点为先进后出,后进先出(LIFO:last in first out)。

程序中的栈结构:

  • 函数调用栈:A(B(C(D()))):即A函数中调用B,B调用C,C调用D;在A执行的过程中会将A压入栈,随后B执行时B也被压入栈,函数C和D执行时也会被压入栈。所以当前栈的顺序为:A->B->C->D(栈顶);函数D执行完之后,会弹出栈被释放,弹出栈的顺序为D->C->B->A;
  • 递归:为什么没有停止条件的递归会造成栈溢出?比如函数A为递归函数,不断地调用自己(因为函数还没有执行完,不会把函数弹出栈),不停地把相同的函数A压入栈,最后造成栈溢出(Stack Overfloat)

3.练习:题目:有6个元素6,5,4,3,2,1按顺序进栈,问下列哪一个不是合法的出栈顺序?

  • A:5 4 3 6 1 2 (√)
  • B:4 5 3 2 1 6 (√)
  • C:3 4 6 5 2 1 (×)
  • D:2 3 4 1 5 6 (√)

题目所说的按顺序进栈指的不是一次性全部进栈,而是有进有出,进栈顺序为6 -> 5 -> 4 -> 3 -> 2 -> 1。

解析:

  • A答案:65进栈,5出栈,4进栈出栈,3进栈出栈,6出栈,21进栈,1出栈,2出栈(整体入栈顺序符合654321);
  • B答案:654进栈,4出栈,5出栈,3进栈出栈,2进栈出栈,1进栈出栈,6出栈(整体的入栈顺序符合654321);
  • C答案:6543进栈,3出栈,4出栈,之后应该5出栈而不是6,所以错误;
  • D答案:65432进栈,2出栈,3出栈,4出栈,1进栈出栈,5出栈,6出栈。符合入栈顺序;

栈常见的操作:

  • push(element):添加一个新元素到栈顶位置;
  • pop():移除栈顶的元素,同时返回被移除的元素;
  • peek():返回栈顶的元素,不对栈做任何修改(该方法不会移除栈顶的元素,仅仅返回它);
  • isEmpty():如果栈里没有任何元素就返回true,否则返回false;
  • size():返回栈里的元素个数。这个方法和数组的length属性类似;
  • toString():将栈结构的内容以字符串的形式返回。

2.2.封装栈类

代码实现:

    // 封装栈类
    function Stack(){
      // 栈中的属性
      this.items =[]

      // 栈的相关操作
      // 1.push():将元素压入栈
      //方式一(不推荐):给对象添加方法,其他对象不能复用
      // this.push = () => {
      // }

      //方式二(推荐):给Stack类添加方法,能够多对象复用
      Stack.prototype.push = function(element) {
      // 利用数组item的push方法实现Stack类的pop方法
        this.items.push(element)
      }

      // 2.pop():从栈中取出元素
      Stack.prototype.pop = () => {
      // 利用数组item的pop方法实现Stack类的pop方法
        return this.items.pop()
      }

      // 3.peek():查看一下栈顶元素
      Stack.prototype.peek = () => {
        return this.items[this.items.length - 1]
      }

      // 4.isEmpty():判断栈是否为空
      Stack.prototype.isEmpty = () => {
      // 两个小时的教训啊不是this.length(不是Stack对象的length,Stack类没有length属性啊),而是           Stack类中定义的数组items才有length属性呀
        return this.items.length == 0
      }

      // 5.size():获取栈中元素的个数
      Stack.prototype.size = () => {
        return this.items.length
      }

      // 6.toString():以字符串形式输出栈内数据
      Stack.prototype.toString = () => {
        //希望输出的形式:20 10 12 8 7
        let resultString = ''
        for (let i of this.items){
          resultString += i + ' '
        }
        return resultString
      }
    }

测试代码:

 // 栈的使用
    let  s = new Stack()
    s.push(20)
    s.push(10)
    s.push(100)
    s.push(77)
    console.log(s)                                                  //65

    console.log(s.pop());                                           //68
    console.log(s.pop());                                           //69

    console.log(s.peek());                                          //71
    console.log(s.isEmpty());                                       //72

    console.log(s.size());                                          //74
    console.log(s.toString());                                      //75

测试结果:

栈结构的简单应用:

利用栈结构的特点封装十进至转换为二进至的函数:

    //简单应用:
    //封装函数:将十进制转成二进制(十转二的运算最后倒叙取余的特点符合栈'先进后出')
    let dec2bin = decNumber => {
      //1.定义一个栈对象,保存余数
      var  stack = new Stack()

      // 2.循环操作
      while(decNumber > 0){
        // 2.1.获取余数并放入栈中
        stack.push(decNumber % 2)
        // 2.2.获取整除后的结果作为下一次运算的数字(floor:向下取整)
        decNumber = Math.floor(decNumber / 2)
      }

      // 3.从栈中取出0和1
      let  binaryString = '';
      let a = stack.items.length
     while(stack.items.length != 0){
        binaryString += stack.pop();
      }
      return binaryString;
    }

    //测试代码
    console.log(dec2bin(10));                                       //103
    console.log(dec2bin(100));                                      //104
    console.log(dec2bin(1000));                                     //105

测试结果:

原文地址:https://www.cnblogs.com/AhuntSun-blog/p/12422941.html

时间: 2024-08-29 09:24:02

JavaScript实现栈结构(Stack)的相关文章

javascript使用栈结构把忠置表达式转后为后置表达式并计算值

1.概念 你可能听说过表达式,a+b,a+b*c这些,但是前缀表达式,前缀记法,中缀表达式,波兰式,后缀表达式,后缀记法,逆波兰式这些都是也是表达式. a+b,a+b*c这些看上去比较正常的是中缀表达式,就是运算符放在两个操作数之间.前缀表达式是将运算符放在相关操作数之前,后缀表达式是将运算符放在操作数之后. 至于前面说的那些概念: 前缀表达式就是波兰式就是前缀记法 后缀表达式就是逆波兰式就是后缀记法 举例如下: (3+4)*5-6就是中缀表达式 -*+3456就是前缀表达式 34+5*6-就是

javascript中的栈结构

1.栈的定义 栈是一种和列表类似的数据结构,可以用它来解决很多的编程问题,栈是一种高效的数据结构,因为数据只能在栈的顶端添加或者删除,所以这样的操作很快而且容易实现. 栈是一种特殊的列表,站内的元素只能拖过列表的一端进行访问,这一端陈伟栈顶.一叠盘子是最常见的栈结构,只能从顶部取盘子,洗好的盘子也只能放在顶端.栈被称为后入先出的数据结构. 由于栈具有后入先出的特点,所以任何不在栈顶的元素都无法访问.为了得到栈底的元素,必须拿掉上面的元素. 对栈的操作有将一个元素压入栈和将一个元素弹出栈.压入栈使

JavaScript实现队列结构(Queue)

JavaScript实现队列结构(Queue) 一.队列简介 队列是是一种受限的线性表,特点为先进先出(FIFO:first in first out). 受限之处在于它只允许在表的前端(front)进行删除操作: 在表的后端(rear)进行插入操作: 相当于排队买票,先来的先买票,后来的后买票. 队列的应用: 打印队列:计算机打印多个文件的时候,需要排队打印: 线程队列:当开启多线程时,当新开启的线程所需的资源不足时就先放入线程队列,等待CPU处理: 队列类的实现: 队列的实现和栈一样,有两种

闭关修炼中 *** Java常用算法之 -- 栈结构

什么是栈结构: 栈结构从数据的运算来分类,栈结构具有特殊的运算规则. 从数据的逻辑结构来看,栈结构其实就是一种线性结构. but!!! 从数据的存储结构来划分,栈结构分为两类: 顺序表结构:即用一组地址连续的内存单元依次保存栈中的数据.在程序中,可以定义一个 指定大小的结构数组来作为栈,序号为0的元素就是栈底,在定义一个top保 存栈顶的序号. 链式栈结构:即使用链式形式保存栈中各元素的值.链表首部(head引用所指向元素)为栈顶, 链表尾部(指向地址为null)为栈底. 栈结构遵循:后进先出(

使用泛型实现栈结构

泛型类就是含有一个或者多个类型参数的类.定义泛型类很简单,只需要在类的名称后面加上"<"和">",并在其中指明类型参数,比如本例中的T. 也可以在其中指明多个参数,如K.V.多个参数之间使用逗号隔开.定义完类后,就可以在类中的域和方法中使用泛型参数. 注意: 泛型类型的参数只能使用类类型,而不能使用基本类型. 设计过程: 1)编写泛型类Stack,在该类中定义了3个方法,分别用来入栈的push()方法.用来出栈的pop()方法和用来判断栈是否为空的emp

栈结构的经典算法题

栈结构 颠倒一个栈的元素顺序 问题:假设有一个栈{1,2,3,4,5,6},6是栈顶,1是栈底,现在要把这个栈中的元素颠倒一下. 思路:最简单的办法当然是把栈中的元素依次pop到一个数组中,然后把这个数组再push回栈里面即可,但这样需要O(n)的辅助空间. 下面介绍一种仅使用O(1)辅助空间的算法,我们知道,可以使用递归来模拟栈的操作.我们借助函数递归pop元素,这样在递归的函数栈上依次有 {6,5,4,3,2,1},1是栈顶,6是栈底,然后在递归返回的时候,如何把当前元素塞到原栈的底部呢?这

C语言实现使用静态数组来构造栈结构

在数据结构中,栈是一种很重要的存在.这是一种先进后出的结构,就像一个"死胡同"一样.今天我们先用最简单的方式静态数组来模拟栈.代码上传至 https://github.com/chenyufeng1991/Stack_StaticArray . (1)声明栈的大小,数组,和一个栈顶指针.栈顶指针可以取出栈顶的数据. #define STACK_SIZE 50 static int stack[STACK_SIZE]; static int top_element = -1; (2)压入

用栈结构实现多项式计算器

学校数据结构课程实验之一. 用到的数据结构:栈 基本功能: 输入中缀的运算表达式(即运算符在操作数中间,符合日常的书写习惯),将其转为逆波兰表达式(后缀表达式,适于机器运算): 对输入的表达式进行括号匹配检查,若不符合规则,报错:对于符合规则的表达式,计算结果并输出: 过滤输入的非法字符(字母). 概要设计: 主函数代码(main.cpp): 1 #include <iostream> 2 #include "MyStack.cpp" 3 #include "Ca

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

[版权申明]转载请注明出处(请尊重原创,博主保留追究权) http://blog.csdn.net/javazejian/article/details/53362993 出自[zejian的博客] 关联文章: java数据结构与算法之顺序表与链表设计与实现分析 java数据结构与算法之双链表设计与实现 java数据结构与算法之改良顺序表与双链表类似ArrayList和LinkedList(带Iterator迭代器与fast-fail机制) java数据结构与算法之栈设计与实现 ??本篇是jav