zoukankan      html  css  js  c++  java
  • 栈与队列

    最近一直在看数据结构与算法,下面是对有线性结构的栈与队列的总结:

    栈相关的内容

    定义:栈是限定仅在表尾进行插入和删除操作的线性表。(后进先出的线性表)

    操作:在可以插入与删除的一端称为栈顶,另外一端称为栈底, 栈的插入称为进栈,栈的删除称为出栈。

    图解:A,B,C依次入栈,然后依次出栈得到C,B,A 如图所示:

    栈的存储结构:栈通常有顺序栈和链栈两种存储结构

    1. 顺序存储结构:通过数组实现,只准栈顶进出元素,不过由于数组的大小是事先确定的,而且需要连续的空间,当容量不过时需要手动扩展。

    java实现代码:

    public class Stack {
        private int maxSize; // size of stack array
        private double[] stackArray;
        private int top;     // top of stack
        public Stack(int s) // constructor
        {
            maxSize = s;     // set array size
            stackArray = new double[maxSize]; // create array
            top = -1;         // no items yet
        }
        public void push(double j) // put item on top of stack
        {
            stackArray[++top] = j; // increment top, insert item
        }
        public double pop()         // take item from top of stack
        {
            return stackArray[top--]; // access item, decrement top
        }
        public double peek()         // peek at top of stack
        {
            return stackArray[top];
        }
        public boolean isEmpty()    // true if stack is empty
        {
            return (top == -1);
        }
        public boolean isFull()     // true if stack is full
        {
            return (top == maxSize-1);
        }
    }
    class StackApp{
        public static void main(String[] args){
            Stack theStack = new Stack(10); // make new stack
            theStack.push(20);                 // push items onto stack
            theStack.push(40);
            theStack.push(60);
            theStack.push(80);
            while( !theStack.isEmpty() ){   // delete item from stack
                double value = theStack.pop();
                System.out.print(value);    // display it
                System.out.print(" ");
            }                                 // end while
            System.out.println("");
        } 
    } 
    //the result:80.0 60.0 40.0 20.0
    

     2.链式存储结构:通过链表实现,最大的优点是存储空间不固定可以伸缩。 

    class Link{
        public double dData;   // data item
        public Link next;      // next link in list
    
        public Link(double dd){// constructor 
            dData = dd;
        }
    
        public void displayLink(){ // display ourself
            System.out.print(dData + " "); 
        }
    } // end class Link
    class LinkList{
        private Link first;  // ref to first item on list
        public LinkList(){   // constructor
            first = null;
        }                    // no items on list yet
        public boolean isEmpty(){ // true if list is empty
            return (first==null);
        }
        public void insertFirst(double dd){ // insert at start of list     
            Link newLink = new Link(dd);  // make new link
            newLink.next = first;      // newLink --> old first
            first = newLink;         // first --> newLink
        }
        public double deleteFirst(){  // delete first item
            Link temp = first;     // save reference to link
            first = first.next;       // delete it: first-->old next
            return temp.dData;        // return deleted link
        }
        public void displayList(){
            Link current = first;         // start at beginning of list
            while(current != null)        // until end of list,
            {
                current.displayLink();    // print data
                current = current.next;   // move to next link
            }
            System.out.println("");
        }
    }                                     // end class LinkList
    class LinkStack
    {
        private LinkList theList;
        public LinkStack(){               // constructor    
            theList = new LinkList();
        }
        public void push(double j){       // put item on top of stack
            theList.insertFirst(j);
        }
        public double pop(){              // take item from top of stack
            return theList.deleteFirst();
        }
        public boolean isEmpty(){         // true if stack is empty
            return ( theList.isEmpty() );
        }
        public void displayStack(){
            System.out.print("Stack (top-->bottom): ");
            theList.displayList();
        }
    }                                    // end class LinkStack
    class LinkStackApp
    {
        public static void main(String[] args) throws IOException{
            LinkStack theStack = new LinkStack(); // make stack
            theStack.push(20);          // push items
            theStack.push(40);
            theStack.displayStack();    // display stack
            theStack.push(60);          // push items
            theStack.push(80);
            theStack.displayStack();    // display stack
            theStack.pop();             // pop items
            theStack.pop();
            theStack.displayStack();    // display stack
        }                              // end main()
    }
    //the result:
    //Stack (top-->bottom): 40.0 20.0 
    //Stack (top-->bottom): 80.0 60.0 40.0 20.0 
    //Stack (top-->bottom): 40.0 20.0
    
    队列相关的内容

    定义:只允许在一端进行插入操作,而在另一端进行删除操作的线性表。(先进先出的线性表)

    操作:可以插入的一端称为队尾,可以删除的一端称为队头,栈的插入称为入队,栈的删除称为出队。

    图解:

    队列的存储结构:队列通常也有顺序和链式两种存储结构

    1. 顺序存储结构:

    我们在队尾进行插入,在队头进行删除,因此必须保证队头元素在数组下标为0的位置处,故要将队列中的每个元素向前移动一个位置

    此时,会有涉及到一个问题,即性能问题,在队尾插入一个元素,不需要移动任何元素,时间复杂度是O[1],但是在队头删除一个元素,要队列中所有的元素都要向前移动一个位置,确保下标为0的位置不为空,时间复杂度是O[n],如果我们不限定出队操作时所有的元素都要向前移动,即通过移动front,rear来控制队头与队尾所在的位置。

    如图,我删除队头元素a0,然后自增front,将a1作为新的队头,则可以免去移动队列中元素所带来的性能损耗。

    然后此时,新的问题产生了,即假溢出,就是front一直增加时间,直到rear没有位置进行插入,队尾入队已经满了。图如下:

    于是引入了循环队列,后面满了,就从头再开始,也就是头尾相接的循环,这种头尾相接的顺序存储结构称为循环队列。

    注意:因为用的是数组,所以还会面临一个数组溢出的问题。

    java实现代码:

    class Queues
    {
        private int maxSize;
        private int[] queArray;
        private int front;
        private int rear;
        public Queues(int s){     // constructor    
            maxSize = s+1;         // array is 1 cell larger
            queArray = new int[maxSize]; // than requested
            front = 0;
            rear = -1;
        }
        public void insert(int j){     // put item at rear of queue    
            if(rear == maxSize-1)
            rear = -1;
            queArray[++rear] = j;
        }
        public int remove(){         // take item from front of queue    
            int temp = queArray[front++];
            if(front == maxSize)
            front = 0;
            return temp;
        }
        public int peek(){             // peek at front of queue    
            return queArray[front];    
        }
        public boolean isEmpty(){     // true if queue is empty    
            return ( rear+1==front || (front+maxSize-1==rear) );
        }
        public boolean isFull(){     // true if queue is full    
            return ( rear+2==front || (front+maxSize-2==rear) );
        }
        public int size(){             // (assumes queue not empty)    
            if(rear >= front)         // contiguous sequence
            return rear-front+1;
            else                     // broken sequence
            return (maxSize-front) + (rear+1);
        }
    } // end class Queue
    
    class QueueApp
    {
        public static void main(String[] args)
        {
            Queues theQueue = new Queues(5); // queue holds 5 items
            theQueue.insert(10);              // insert 4 items
            theQueue.insert(20);
            theQueue.insert(30);
            theQueue.insert(40);
            theQueue.remove();                  // remove 3 items
            theQueue.remove();                  // (10, 20, 30)
            theQueue.remove();
            theQueue.insert(50);              // insert 4 more items
            theQueue.insert(60);              // (wraps around)
            theQueue.insert(70);
            theQueue.insert(80);
            while( !theQueue.isEmpty() )      // remove and display
            {                                  // all items
                int n = theQueue.remove();   // (40, 50, 60, 70, 80)
                System.out.print(n);
                System.out.print(" ");
                }
                System.out.println("");
            }                                  // end main()
    }                                          // end class QueueApp
    //the result:40 50 60 70 80
    

    2.链式存储结构:通过线性表中的单链表经行实现,尾进头出。

    代码:

    class Link
    {
        public double dData;         // data item
        public Link next;            // next link in list
        public Link(double d){       // constructor
            dData = d;
        }
        public void displayLink(){  // display this link
            System.out.print(dData + " ");
        }
    }                                // end class Link
    class FirstLastList{
        private Link first;         // ref to first item
        private Link last;          // ref to last item
        public FirstLastList(){     // constructor
            first = null;           // no items on list yet
            last = null;
        }
        public boolean isEmpty(){   // true if no links
            return first==null;
        }
        public void insertLast(double dd){ // insert at end of list
            Link newLink = new Link(dd);   // make new link
            if( isEmpty() )                // if empty list,
            first = newLink;               // first --> newLink
            else
            last.next = newLink;           // old last --> newLink
            last = newLink;                // newLink <-- last
        }
        public double deleteFirst(){       // delete first link
            double temp = first.dData;
            if(first.next == null)         // if only one item
            last = null;                   // null <-- last
            first = first.next;            // first --> old next
            return temp;
        }
        public void displayList(){
            Link current = first;        // start at beginning
            while(current != null){      // until end of list,
                current.displayLink();   // print data
                current = current.next;  // move to next link
            }
            System.out.println("");
        }
    }                                    // end class FirstLastList
    class LinkQueue
    {
        private FirstLastList theList;
        public LinkQueue(){                // constructor
            theList = new FirstLastList(); // make a 2-ended list
        }
        public boolean isEmpty(){          // true if queue is empty
            return theList.isEmpty();
        }
        public void insert(double j){      // insert, rear of queue
            theList.insertLast(j);
        }
        public double remove(){            // remove, front of queue
            return theList.deleteFirst();
        }
        public void displayQueue(){
            System.out.print("Queue (front-->rear): ");
            theList.displayList();
        }
    }                                    // end class LinkQueue
    class LinkQueueApp
    {
        public static void main(String[] args) throws IOException{
            LinkQueue theQueue = new LinkQueue();
            theQueue.insert(20);         // insert items
            theQueue.insert(40);
    
            theQueue.displayQueue();     // display queue
            theQueue.insert(60);         // insert items
            theQueue.insert(80);
            theQueue.displayQueue();     // display queue
            theQueue.remove();           // remove items
            theQueue.remove();
            theQueue.displayQueue();     // display queue
        }                                // end main()
    }                                    // end class LinkQueueApp
    //the result:
    //Queue (front-->rear): 20.0 40.0 
    //Queue (front-->rear): 20.0 40.0 60.0 80.0 
    //Queue (front-->rear): 60.0 80.0
    
  • 相关阅读:
    12 Essential Bootstrap Tools for Web Designers
    S.O.L.I.D 是面向对象设计(OOD)和面向对象编程(OOP)中的几个重要编码原则
    cocos2d3.0rc编译android工程
    Android和iOS中Cocos2dx的横屏竖屏设置
    cocos2d-x 3.0rc开发指南:Windows下Android环境搭建
    C#第一个windows窗体应用程序
    程序员技术练级攻略
    11个强大的Visual Studio调试小技巧
    Model--汇总
    UIView---汇总
  • 原文地址:https://www.cnblogs.com/Swen3252/p/9493444.html
Copyright © 2011-2022 走看看