Java实现三种(顺序,链式,循环)队列

本文详细介绍了如何使用Java实现三种队列:顺序队列、链式队列和循环队列。通过实例代码,阐述了各种队列的数据结构特性和操作方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1.顺序队列的实现

package lang;  

import java.io.Serializable;  
import java.util.Arrays;  

/** 
 * @ClassName: ArrayQueue 
 * @Description: 顺序队列 
 * @date 2014年1月20日 下午3:46:19 
 * @param <T> 
 */  
public class ArrayQueue<T> implements Serializable{  
  /** 
   * @Fields serialVersionUID : TODO 
   */  
  private static final long serialVersionUID = 7333344126529379197L;  

  private int DEFAULT_SIZE = 10;  

  private int capacity;//保存数组的长度  

  private Object[] elementData;//定义一个数组用于保存顺序队列的元素  

  private int front = 0;//队头  

  private int rear = 0;//队尾  

  //以默认数组长度创建空顺序队列  
  public ArrayQueue() {  
    capacity = DEFAULT_SIZE;  
    elementData = new Object[capacity];  
  }  

  //以一个初始化元素来创建顺序队列  
  public ArrayQueue(T element) {  
    this();  
    elementData[0] = element;  
    rear++;  
  }  

  public ArrayQueue(int initSize) {  
    elementData = new Object[initSize];  
  }  

  /** 
   * 以指定长度的数组来创建顺序队列 
   * @param element 指定顺序队列中第一个元素 
   * @param initSize 指定顺序队列底层数组的长度 
   */  
  public ArrayQueue(T element, int initSize) {  
    this.capacity = initSize;  
    elementData = new Object[capacity];  
    elementData[0] = element;  
    rear++;  
  }  

  /** 
   * @Title: size      
   * @Description: 获取顺序队列的大小     
   * @return 
   */  
  public int size() {  
    return rear - front;  
  }  

  /** 
   * @Title: offer      
   * @Description: 入队     
   * @param element 
   */  
  public void offer(T element) {  
    ensureCapacity(rear + 1);  
    elementData[rear++] = element;  
  }  

  private void ensureCapacity(int minCapacity) {  
    //如果数组的原有长度小于目前所需的长度  
    int oldCapacity = elementData.length;  
    if (minCapacity > oldCapacity) {  
      int newCapacity = (oldCapacity * 3) / 2 + 1;  
      if (newCapacity < minCapacity)  
        newCapacity = minCapacity;  
      // minCapacity is usually close to size, so this is a win:  
      elementData = Arrays.copyOf(elementData, newCapacity);  
    }  

  }  

  /** 
   * @Title: poll      
   * @Description: 出队     
   * @return 
   */  
  public T poll() {  
    if (isEmpty()) {  
      throw new IndexOutOfBoundsException("空队列异常");  
    }  
    //保留队列的front端的元素的值  
    T oldValue = (T) elementData[front];  
    //释放队列的front端的元素  
    elementData[front++] = null;  
    return oldValue;  
  }  

  /** 
   * @Title: peek      
   * @Description: 返回队列顶元素,但不删除队列顶元素     
   * @return 
   */  
  public T peek() {  
    if (isEmpty()) {  
      throw new IndexOutOfBoundsException("空队列异常");  
    }  
    return (T) elementData[front];  
  }  

  /** 
   * @Title: isEmpty      
   * @Description: 判断顺序队列是否为空队列     
   * @return 
   */  
  public boolean isEmpty() {  
    return rear == front;  
  }  

  /** 
   * @Title: clear      
   * @Description: 清空顺序队列 
   */  
  public void clear() {  
    //将底层数组所有元素赋为null  
    Arrays.fill(elementData, null);  
    front = 0;  
    rear = 0;  
  }  

  public String toString() {  
    if (isEmpty()) {  
      return "[]";  
    } else {  
      StringBuilder sb = new StringBuilder("[");  
      for (int i = front; i < rear; i++) {  
        sb.append(elementData[i].toString() + ", ");  
      }  
      int len = sb.length();  
      return sb.delete(len - 2, len).append("]").toString();  
    }  
  }  
}  

2. 链式队列的实现

package lang;  

import java.io.Serializable;  

/** 
 * @ClassName: LinkQueue 
 * @Description:  链式队列 
 * @date 2014年1月21日 下午3:24:38 
 * @param <T> 
 */  
public class LinkQueue<T> implements Serializable{  
  /** 
   * @Fields serialVersionUID : TODO 
   */  
  private static final long serialVersionUID = -6726728595616312615L;  

  //定义一个内部类Node,Node实例代表链队列的节点。  
  private class Node {  

    private T data;//保存节点的数据  

    private Node next;//指向下个节点的引用  

    //无参数的构造器  
    public Node() {  
    }  

    //初始化全部属性的构造器  
    public Node(T data, Node next) {  
      this.data = data;  
      this.next = next;  
    }  
  }  

  private Node front;//保存该链队列的头节点  

  private Node rear;//保存该链队列的尾节点  

  private int size;//保存该链队列中已包含的节点数  

  /** 
   * <p>Title: LinkQueue </p>      
   * <p>Description: 创建空链队列 </p>  
   */  
  public LinkQueue() {  
    //空链队列,front和rear都是null  
    front = null;  
    rear = null;  
  }  

  /** 
   * <p>Title: LinkQueue </p>     
   * <p>Description: 以指定数据元素来创建链队列,该链队列只有一个元素</p>  
   */  
  public LinkQueue(T element) {  
    front = new Node(element, null);  
    //只有一个节点,front、rear都指向该节点  
    rear = front;  
    size++;  
  }  

  /** 
   * @Title: size      
   * @Description: 获取顺序队列的大小     
   * @return 
   */  
  public int size() {  
    return size;  
  }  

  /** 
   * @Title: offer      
   * @Description: 入队     
   * @param element 
   */  
  public void offer(T element) {  
    //如果该链队列还是空链队列  
    if (front == null) {  
      front = new Node(element, null);       
      rear = front;//只有一个节点,front、rear都指向该节点  
    } else {       
      Node newNode = new Node(element, null);//创建新节点       
      rear.next = newNode;//让尾节点的next指向新增的节点       
      rear = newNode;//以新节点作为新的尾节点  
    }  
    size++;  
  }  

  /** 
   * @Title: poll      
   * @Description: 出队     
   * @return 
   */  
  public T poll() {  
    Node oldFront = front;  
    front = front.next;  
    oldFront.next = null;  
    size--;  
    return oldFront.data;  
  }  

  /** 
   * @Title: peek      
   * @Description: 返回队列顶元素,但不删除队列顶元素     
   * @return 
   */  
  public T peek() {  
    return rear.data;  
  }  

  /** 
   * @Title: isEmpty      
   * @Description: 判断顺序队列是否为空队列     
   * @return 
   */  
  public boolean isEmpty() {  
    return size == 0;  
  }  

  /** 
   * @Title: clear      
   * @Description: 清空顺序队列 
   */  
  public void clear() {  
    //将front、rear两个节点赋为null  
    front = null;  
    rear = null;  
    size = 0;  
  }  

  public String toString() {  
    //链队列为空链队列时  
    if (isEmpty()) {  
      return "[]";  
    } else {  
      StringBuilder sb = new StringBuilder("[");  
      for (Node current = front; current != null; current = current.next) {  
        sb.append(current.data.toString() + ", ");  
      }  
      int len = sb.length();  
      return sb.delete(len - 2, len).append("]").toString();  
    }  
  }  

  public static void main(String[] args) {  
    LinkQueue<String> queue = new LinkQueue<String>("aaaa");  
    //添加两个元素  
    queue.offer("bbbb");  
    queue.offer("cccc");  
    System.out.println(queue);  
    //删除一个元素后  
    queue.poll();  
    System.out.println("删除一个元素后的队列:" + queue);  
    //再次添加一个元素  
    queue.offer("dddd");  
    System.out.println("再次添加元素后的队列:" + queue);  
    //删除一个元素后,队列可以再多加一个元素  
    queue.poll();  
    //再次加入一个元素  
    queue.offer("eeee");  
    System.out.println(queue);  
  }  
}  

3. 循环队列的实现

package lang;  

import java.io.Serializable;  
import java.util.Arrays;  

/** 
 * @ClassName: LoopQueue 
 * @Description: 循环队列 
 * @date 2014年1月20日 下午3:47:14 
 */  
public class LoopQueue<T> implements Serializable{  
  /** 
   * @Fields serialVersionUID : TODO 
   */  
  private static final long serialVersionUID = -3670496550272478781L;  

  private int DEFAULT_SIZE = 10;  

  private int capacity;//保存数组的长度  

  private Object[] elementData;//定义一个数组用于保存循环队列的元素  

  private int front = 0;//队头  

  private int rear = 0;//队尾  

  //以默认数组长度创建空循环队列  
  public LoopQueue() {  
    capacity = DEFAULT_SIZE;  
    elementData = new Object[capacity];  
  }  

  //以一个初始化元素来创建循环队列  
  public LoopQueue(T element) {  
    this();  
    elementData[0] = element;  
    rear++;  
  }  

  /** 
   * 以指定长度的数组来创建循环队列 
   * @param element 指定循环队列中第一个元素 
   * @param initSize 指定循环队列底层数组的长度 
   */  
  public LoopQueue(T element, int initSize) {  
    this.capacity = initSize;  
    elementData = new Object[capacity];  
    elementData[0] = element;  
    rear++;  
  }  

  //获取循环队列的大小  
  public int size() {  
    if (isEmpty()) {  
      return 0;  
    }  
    return rear > front ? rear - front : capacity - (front - rear);  
  }  

  //插入队列  
  public void add(T element) {  
    if (rear == front && elementData[front] != null) {  
      throw new IndexOutOfBoundsException("队列已满的异常");  
    }  
    elementData[rear++] = element;  
    //如果rear已经到头,那就转头  
    rear = rear == capacity ? 0 : rear;  
  }  

  //移除队列  
  public T remove() {  
    if (isEmpty()) {  
      throw new IndexOutOfBoundsException("空队列异常");  
    }  
    //保留队列的rear端的元素的值  
    T oldValue = (T) elementData[front];  
    //释放队列的rear端的元素  
    elementData[front++] = null;  
    //如果front已经到头,那就转头  
    front = front == capacity ? 0 : front;  
    return oldValue;  
  }  

  //返回队列顶元素,但不删除队列顶元素  
  public T element() {  
    if (isEmpty()) {  
      throw new IndexOutOfBoundsException("空队列异常");  
    }  
    return (T) elementData[front];  
  }  

  //判断循环队列是否为空队列  
  public boolean isEmpty() {  
    //rear==front且rear处的元素为null  
    return rear == front && elementData[rear] == null;  
  }  

  //清空循环队列  
  public void clear() {  
    //将底层数组所有元素赋为null  
    Arrays.fill(elementData, null);  
    front = 0;  
    rear = 0;  
  }  

  public String toString() {  
    if (isEmpty()) {  
      return "[]";  
    } else {  
      //如果front < rear,有效元素就是front到rear之间的元素  
      if (front < rear) {  
        StringBuilder sb = new StringBuilder("[");  
        for (int i = front; i < rear; i++) {  
          sb.append(elementData[i].toString() + ", ");  
        }  
        int len = sb.length();  
        return sb.delete(len - 2, len).append("]").toString();  
      }  
      //如果front >= rear,有效元素为front->capacity之间、0->front之间的  
      else {  
        StringBuilder sb = new StringBuilder("[");  
        for (int i = front; i < capacity; i++) {  
          sb.append(elementData[i].toString() + ", ");  
        }  
        for (int i = 0; i < rear; i++) {  
          sb.append(elementData[i].toString() + ", ");  
        }  
        int len = sb.length();  
        return sb.delete(len - 2, len).append("]").toString();  
      }  
    }  
  }  

  public static void main(String[] args) {  
    LoopQueue<String> queue = new LoopQueue<String>("aaaa", 3);  
    //添加两个元素  
    queue.add("bbbb");  
    queue.add("cccc");  
    //此时队列已满  
    System.out.println(queue);  
    //删除一个元素后,队列可以再多加一个元素  
    queue.remove();  
    System.out.println("删除一个元素后的队列:" + queue);  
    //再次添加一个元素,此时队列又满  
    queue.add("dddd");  
    System.out.println(queue);  
    System.out.println("队列满时的长度:" + queue.size());  
    //删除一个元素后,队列可以再多加一个元素  
    queue.remove();  
    //再次加入一个元素,此时队列又满  
    queue.add("eeee");  
    System.out.println(queue);  
  }  
}  
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值