欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

基于链表结构实现先进先出 队列

程序员文章站 2024-03-17 15:34:34
...

基于链表结构实现先进先出 队列

上文中讲到了如何基于链表结构实现一个栈的数据结构,参考:下压堆栈(链表实现),本篇介绍如何如何实现队列结构。

队列应用:

  • 生活中各种排队场景:食堂排队,银行排队。。。排队意味着公平。VIP除外
  • 常言道:先来后到,先到先得。都是一种队列思想

实现思路:

  • 定义两个实例变量,first和last,分别指向链表的表头和表尾,同时代表队列的队头和队尾。
  • 队列规定,队尾只许插入元素,队头只许删除元素,也就是说,新来的结点元素放在表尾(入队),而要从队列中取出元素(出队),只许在表头取。
    基于链表结构实现先进先出 队列

直接上代码:

import java.util.Iterator;
import java.util.Scanner;

/**
 * @author zhangjinglong
 * @date 2019-06-11-20:21
 * 先进先出队列  链表实现
 */

public class Queue<Item> implements Iterable<Item> {
    private Node first;//指向最早添加的结点的链接 表头
    private Node last;//指向最近添加的结点的链接 表尾
    private int N;//队列中的元素数量
    private class Node{
        //定义了链表结点的嵌套类
        Item item;//保存数据的值
        Node next;//指向链表的下个结点
    }

    public boolean isEmpty(){
        return first==null; //或者用  N==0

    }

    public int size(){return N;}

    public void enqueue(Item item){
       //向表尾添加元素
       Node oldlast=last;//定义变量暂时保存原来的表尾
       last=new Node();//创建一个新结点,引用赋给last
       last.item=item;
       last.next=null;
       if(isEmpty()) first=last;//如果队列中没有元素,则first和last都指向同一个结点
        else oldlast.next=last;//将队尾的next值指向新的结点
        N++;//队列元素+1
    }

    public Item dequeue(){
        //从表头删除元素
        Item item=first.item;//创建变量保存表头元素
        first=first.next;//移除表头结点
        if(isEmpty()) last=null;//如果队列为空,则last也赋值为null
        N--;
        return item;


    }

    public Iterator<Item> iterator(){//实现Iterable的接口方法
        return new ListIterator();

    }
    private class ListIterator implements Iterator<Item>{//定义返回的迭代器
        private Node current=first;//复制一份头结点引用,初始化current
        public boolean hasNext(){return current.next!=null;}
        public void remove(){}
        public Item next(){
            Item item=current.item;//保留当前指向结点的值,用以返回
            current=current.next;//指向下一结点
            return item;
        }

    }

    //测试用例
    public static void main(String[] args) {
        //创建一个队列并操作字符串入列或出列
        Queue<String> q=new Queue<>();
        Scanner scanner= new Scanner(System.in);

        while(true){
            if(scanner.hasNext()){
                String item=scanner.next();
                if(item.equals("!")){// !表示终止输入
                    break;
                }else if( item.equals("-")){
                    if(q.isEmpty()){
                        System.out.println("the queue is empty!");
                    }else{
                        System.out.println(q.dequeue()+ " ");
                    }
                }else{
                    q.enqueue(item);
                }

            }
        }

        System.out.println("("+q.size()+ " left on queue)");
    }

}