当前位置:   article > 正文

【java-数据结构19-队列的模拟实现】

【java-数据结构19-队列的模拟实现】

  上篇文章,小编已经带大家一起认识了队列,并且对队列的方法进行调用测试,下面我们将模拟实现一个队列,话不多说,上正文~

1.队列的模拟实现

  队列的实现方法和链表的实现方式一模一样,这里我们首选双链表,前驱,后继,参数,头,尾,构造方法,这里就不多做赘述了,直接上代码~

  1. public class MyQueue {
  2. static class ListNode{
  3. private int val;
  4. private ListNode prev;
  5. private ListNode next;
  6. public ListNode(int val){
  7. this.val = val;
  8. }
  9. }
  10. private ListNode front;
  11. private ListNode rear;
  12. public int usedSize ;
  13. }

2.插入数据

  这里我们要用到的是头插法,前面提到。我们自己模拟实现的队列底层是一个双向链表,那么双向链表的头插我们前面也提到过,这里我们再复述一遍~

 这里我们先定义一个 node节点,如图

接下来就是改节点,和具体代码

 然而,只是这样,我们还忘记了一个重要细节,如果head为空,那么node就是整个链表的头,也是整个链表的尾,如图

代码如下

  1. public void offer(int x){
  2. ListNode node = new ListNode(x);
  3. if(front == null) {
  4. front = rear = node;
  5. }else {
  6. node.next = front;
  7. front.prev = node;
  8. front = node;
  9. }
  10. usedSize++;
  11. }
  12. }

调用测试

  1. public static void main(String[] args) {
  2. MyQueue myQueue = new MyQueue();
  3. myQueue.offer(1);
  4. myQueue.offer(2);
  5. myQueue.offer(3);
  6. myQueue.offer(4);
  7. System.out.println();
  8. }

运行截图

 注意,由于我们是头插法,实际存储数据为:4,3,2,1

3.弹出数据 

1.删第一个数据(此方法比较不合理,不常用,大家了解即可,下面的删除头节点才是重点)

  同样的,双向链表一样,考虑没有节点的情况(直接返回或抛出异常),只有一个节点的情况(将头,尾全部置空),和普通情况(front向后走,front前驱置为空)

代码如下

  1. public int pop(){
  2. //没有节点
  3. if (front == null){
  4. return -1;
  5. }
  6. int ret = front.val;//存下数据
  7. //只有一个节点
  8. if (front == rear){
  9. front= null;
  10. rear = null;
  11. usedSize--;
  12. }
  13. //至少有两个节点
  14. front=front.next;
  15. front.prev = null;
  16. usedSize--;
  17. return ret;
  18. }

调用测试

  1. public static void main(String[] args) {
  2. MyQueue myQueue = new MyQueue();
  3. myQueue.offer(1);
  4. myQueue.offer(2);
  5. myQueue.offer(3);
  6. myQueue.offer(4);
  7. System.out.println();
  8. System.out.println(myQueue.pop());
  9. }

运行截图

2.删除最后一个元素 (这个才是重点)

同上,没有元素直接返回即可,只有一个元素(全部置空),普通情况(rear等于前驱,rear置为空),此时存下的数据也要改变

代码如下

  1. public int pop(){
  2. //没有节点
  3. if (front == null){
  4. return -1;
  5. }
  6. int ret = rear.val;//存下数据
  7. //只有一个节点
  8. if (front == rear){
  9. front= null;
  10. rear = null;
  11. usedSize--;
  12. }
  13. //至少有两个节点
  14. rear = rear.prev;
  15. rear.next = null;
  16. usedSize--;
  17. return ret;
  18. }

调用测试

  1. public class test {
  2. public static void main(String[] args) {
  3. MyQueue myQueue = new MyQueue();
  4. myQueue.offer(1);
  5. myQueue.offer(2);
  6. myQueue.offer(3);
  7. myQueue.offer(4);
  8. System.out.println();
  9. System.out.println(myQueue.pop());
  10. }
  11. }

运行截图

4.获取队头元素 

  首先判空,如果为空,返回-1,如果不为空,返回front的值即可

代码如下

  1. public int peek(){
  2. if (front == null){
  3. return -1;
  4. }
  5. return front.val;
  6. }

调用测试

  1. public class test {
  2. public static void main(String[] args) {
  3. MyQueue myQueue = new MyQueue();
  4. myQueue.offer(1);
  5. myQueue.offer(2);
  6. myQueue.offer(3);
  7. myQueue.offer(4);
  8. System.out.println();
  9. System.out.println(myQueue.peek());
  10. }
  11. }

运行截图

5.返回元数个数,判空 

两种方法不复杂,一个直接返回有效元素个数,一共看usedSize是否为零,代码如下

  1. public int getUsedSize() {
  2. return usedSize;
  3. }
  4. public boolean isEmpty(){
  5. return usedSize == 0;
  6. }

调用测试

  1. public static void main(String[] args) {
  2. MyQueue myQueue = new MyQueue();
  3. myQueue.offer(1);
  4. myQueue.offer(2);
  5. myQueue.offer(3);
  6. myQueue.offer(4);
  7. System.out.println();
  8. System.out.println(myQueue.getUsedSize());
  9. System.out.println(myQueue.isEmpty());
  10. }

运行截图

那么到此为止,本篇文章就到此结束啦~下一篇文章我们将继续学习队列的相关知识,敬请期待叭~觉得小编讲的还可以的可以留个关注支持一下,谢谢观看~

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/我家小花儿/article/detail/626132
推荐阅读
相关标签
  

闽ICP备14008679号