如何在Java中一次性查找Java中链表的中间元素

19-01-26 jdon
         

如何在一次传递中找到LinkedList的中间元素?这是一个Java和非Java程序员面试时经常被问到的编程问题。这个问题类似于检查回文或计算阶乘,有时也会要求编写代码。为了回答这个问题,候选人必须熟悉LinkedList的数据结构,即在单个LinkedList的情况下,链表的每个节点都包含数据和指针,这是下一个链表的地址,而单个链表的最后一个元素指向空值。因为要找到链接列表的中间元素,您需要找到LinkedList的长度,它将元素计数到末尾,即直到找到链接列表的最后一个元素为止。这个数据结构面试问题有趣的是,你需要一次找到LinkedList的中间元素,而你不知道LinkedList的长度。这就是应试者逻辑能力测试的地方,不管他是否熟悉时空权衡等。

你仔细想想你可以通过使用两个指针来解决这个问题,如何在Java中查找单链表的长度。通过使用两个指针,在每次迭代时递增一个,在每次迭代时递增另一个。当第一个指针指向链接列表的末尾时,第二个指针将指向链接列表的中间节点。

事实上,这两个指针方法可以解决多个类似问题,例如如何在一次迭代中找到链接列表中最后一个的第三个元素或如何在链接列表中找到最后一个元素。在这个Java编程教程中,我们将看到一个Java程序,它在一次迭代中找到Linked List的中间元素。

Java程序在一次传递中查找LinkedList的中间元素

如何在Java中找到链表的中间元素,以Java为例,用Java程序找到链表中间节点。记住,LyKeDLead类是我们的自定义类,不要把这个类与JavaUTL.LIKEDLIST混淆,它是Java中一个流行的集合类。在这个Java程序中,我们的类链接表代表一个链表数据结构,它包含节点的集合并具有头部和尾部。每个节点包含数据和地址部分。LIKEDListTestC类的主要方法用于模拟问题,在其中创建链表并在其中添加了几个元素,然后在Java中对它们进行迭代,以一次传递中找到链接列表的中间元素。

import test.LinkedList.Node;

/**
 * Java program to find middle element of linked list in one pass.
 * In order to find middle element of linked list we need to find length first
 * but since we can only traverse linked list one time, we will use two pointers
 * one which we will increment on each iteration while other which will be
 * incremented every second iteration. so when first pointer will point to the
 * end of linked list, second will be pointing to the middle element of linked list
 * @author
 */
public class LinkedListTest {
  
  
    public static void main(String args[]) {
        //creating LinkedList with 5 elements including head
      LinkedList linkedList = new LinkedList();
      LinkedList.Node head = linkedList.head();
      linkedList.add( new LinkedList.Node("1"));
      linkedList.add( new LinkedList.Node("2"));
      linkedList.add( new LinkedList.Node("3"));
      linkedList.add( new LinkedList.Node("4"));
    
      //finding middle element of LinkedList in single pass
      LinkedList.Node current = head;
      int length = 0;
      LinkedList.Node middle = head;
    
      while(current.next() != null){
          length++;
          if(length%2 ==0){
              middle = middle.next();
          }
          current = current.next();
      }
    
      if(length%2 == 1){
          middle = middle.next();
      }

      System.out.println("length of LinkedList: " + length);
      System.out.println("middle element of LinkedList : " + middle);
      
    } 
  
}

class LinkedList{
    private Node head;
    private Node tail;
  
    public LinkedList(){
        this.head = new Node("head");
        tail = head;
    }
  
    public Node head(){
        return head;
    }
  
    public void add(Node node){
        tail.next = node;
        tail = node;
    }
  
    public static class Node{
        private Node next;
        private String data;

        public Node(String data){
            this.data = data;
        }
      
        public String data() {
            return data;
        }

        public void setData(String data) {
            this.data = data;
        }

        public Node next() {
            return next;
        }

        public void setNext(Node next) {
            this.next = next;
        }
      
        public String toString(){
            return this.data;
        }
    }
}

Output:
length of LinkedList: 4
middle element of LinkedList : 2

这就是如何在一次传递中找到LinkedList的中间元素。  此处提到的用于查找LinkedList的中间节点的技术也可用于从LinkedList中的Last或nth元素中找到第3个元素。

         

1