Java 将链接列表分成两半,然后返回后半部分

Java 将链接列表分成两半,然后返回后半部分,java,algorithm,linked-list,Java,Algorithm,Linked List,这是一个编程问题,我做错了。下面给出了部分代码: public class SingleLinkedList<E> { private Node<E> head; private int size = 0; private static class Node<E> { private E data; private Node<E> next; /** Creates a new node with

这是一个编程问题,我做错了。下面给出了部分代码:

public class SingleLinkedList<E> {
   private Node<E> head;
   private int size = 0;

   private static class Node<E> {
     private E data;
     private Node<E> next;

     /** Creates a new node with a null next field
         @param dataItem  The data stored
     */
     private Node(E data) {
       data = dataItem;
       next = null;
     }

    /** Creates a new node that references another node
         @param dataItem  The data stored
         @param nodeRef  The node referenced by new node
     */
     private Node(E dataItem, Node<E> nodeRef) {
       data = dataItem;
       next = nodeRef;
     }
  }

}
公共类单链接列表{
专用节点头;
私有整数大小=0;
私有静态类节点{
私人电子数据;
私有节点下一步;
/**创建下一个字段为空的新节点
@param dataItem存储的数据
*/
专用节点(E数据){
数据=数据项;
next=null;
}
/**创建引用其他节点的新节点
@param dataItem存储的数据
@param nodeRef新节点引用的节点
*/
专用节点(E数据项、节点节点ref){
数据=数据项;
next=nodeRef;
}
}
}
我的任务是创建一个方法,将链表一分为二,将前一半的元素保留在原始列表中,然后返回一个新的SingleLinkedList,其中包含链表的后一半。如果元素数为奇数,然后,额外的元素应该与上半场配合。我做不到。然后,我的老师给出了如下答案:

SingleLinkedList<E> newlist = new SingleLinkedList<E>();
 newlist.head =  temp.next; 
temp.next= null; 
return newlist
SingleLinkedList newlist=newsinglelinkedlist();
newlist.head=temp.next;
温度next=null;
返回新列表

但是,我甚至没有得到答案。我是一个初学者。如果有人能解释这个问题,我将不胜感激。

老师提供的代码不完整。无论如何,我可以给你两种方法来找到指向下半部分的指针:

  • 如果希望指针引用同一列表中的下半部分

    private static Node getSecondHalfInSameList(Node head) {
        Node fastRunner = head, slowRunner = head;
        while(fastRunner != null && fastRunner.next != null) {
            slowRunner = slowRunner.next;
            fastRunner = fastRunner.next.next;
        }
        return slowRunner;
    }
    
  • 如果您想创建一个包含下半部分中所有节点的新列表,那么您可以执行以下操作:首先,我们找到中间节点,然后通过创建从中间节点迭代到列表末尾的新节点,从下半部分创建一个新列表

    private static Node getSecondHalfByCreatingNewNodes(Node head) {
        Node mid = getMiddleNode(head);
        Node newHead = new Node(mid.data);
        mid = mid.next;
        Node tail = newHead, temp;
        while(mid != null) {
            temp = new Node(mid.data);
            tail.next = temp;
            tail = temp;
        }
        return newHead;
    }
    
    private static Node getMiddleNode(Node head) {
        Node fastRunner = head, slowRunner = head;
        while(fastRunner != null && fastRunner.next != null) {
            slowRunner = slowRunner.next;
            fastRunner = fastRunner.next.next;
        }
        return slowRunner;
    }
    

  • 老师提供的代码不完整。无论如何,我可以给你两种方法来找到指向下半部分的指针:

  • 如果希望指针引用同一列表中的下半部分

    private static Node getSecondHalfInSameList(Node head) {
        Node fastRunner = head, slowRunner = head;
        while(fastRunner != null && fastRunner.next != null) {
            slowRunner = slowRunner.next;
            fastRunner = fastRunner.next.next;
        }
        return slowRunner;
    }
    
  • 如果您想创建一个包含下半部分中所有节点的新列表,那么您可以执行以下操作:首先,我们找到中间节点,然后通过创建从中间节点迭代到列表末尾的新节点,从下半部分创建一个新列表

    private static Node getSecondHalfByCreatingNewNodes(Node head) {
        Node mid = getMiddleNode(head);
        Node newHead = new Node(mid.data);
        mid = mid.next;
        Node tail = newHead, temp;
        while(mid != null) {
            temp = new Node(mid.data);
            tail.next = temp;
            tail = temp;
        }
        return newHead;
    }
    
    private static Node getMiddleNode(Node head) {
        Node fastRunner = head, slowRunner = head;
        while(fastRunner != null && fastRunner.next != null) {
            slowRunner = slowRunner.next;
            fastRunner = fastRunner.next.next;
        }
        return slowRunner;
    }
    

  • 这只是答案的一部分,将列表拆分为两个列表的部分。您仍然需要编写代码来找到拆分列表的位置(在解决方案代码中标识为
    temp
    )。给定长度
    n
    列表,您将如何计算分割点的索引?这实际上不是一个编程问题,这是一个基本的算法。写一个方法,在列表中一直写到最后。然后想想如何修改它,使迭代器停在中间。答案是我的老师给出的。我不明白他在说什么。这不是完整答案,这是将列表分成两个列表的方法。你的老师只给了你答案的三分之一第1部分:您需要找到中间点,方法是取列表大小的一半,然后迭代直到找到中间节点,即前一半的最后一个节点(
    temp
    )。第2部分:将链的后半部分指定给新列表(前2行),并终止前半部分的链(第3行)。第3部分:设置两个列表的大小。--你的老师只给了你第二部分,实际上是在误导你,因为作业还没有完成。这只是答案的一部分,将列表分成两个列表的部分。您仍然需要编写代码来找到拆分列表的位置(在解决方案代码中标识为
    temp
    )。给定长度
    n
    列表,您将如何计算分割点的索引?这实际上不是一个编程问题,这是一个基本的算法。写一个方法,在列表中一直写到最后。然后想想如何修改它,使迭代器停在中间。答案是我的老师给出的。我不明白他在说什么。这不是完整答案,这是将列表分成两个列表的方法。你的老师只给了你答案的三分之一第1部分:您需要找到中间点,方法是取列表大小的一半,然后迭代直到找到中间节点,即前一半的最后一个节点(
    temp
    )。第2部分:将链的后半部分指定给新列表(前2行),并终止前半部分的链(第3行)。第3部分:设置两个列表的大小。--你的老师只给了你第2部分,实际上是在误导你,因为作业还没有完成,所以他给你展示了
    return
    语句。