This is the code that I came up with to reverse a singly-linked-list in Java and I am wondering whether it is correctly done. I know that it works as far as doing its job and having the run time of O(n), but is this a right way to do it or what can be improved? Also what can I do to avoid a stack-overflow problem when reversing a long linked list (without using an iterative alternative), because when trying to reverse a linked list of size greater than 8300, it causes a stack-overflow exception.
private void reverse(Node node) {
if(node != this.tail) {
reverse(node.next);
this.tail.next = new Node(node.item);
this.tail = this.tail.next;
this.head = this.head.next;
}
}
public void reverse() {
reverse(this.head);
}
CodePudding user response:
That solution seems fine, however you do not need to create new Node
objects with the values from old Node
objects. You can reverse a singly-linked-list in-place and in O(n)
time complexity.
public Node reverse(Node head) {
Node prev = null;
while(head!= null) {
Node rem = head.next;
head.next = prev;
prev = current;
current = rem;
}
return prev; // prev is the new head of your linked list
}
If you do not want to use an iterative solution (although I'd recommend to do so), you can use recursive solution below:
public Node reverseList(Node node) { // send the head of the list
if(current == null) return null;
reverse(current);
return this.tail; // now tail is the head and head is the tail
}
public Node reverse(Node node) {
if(node.next == null) {
this.tail = node;
} else {
reverse(node.next).next = node;
node.next = null;
}
return node;
}
I don't have enough details about your linked list, but I assume you have this.head
and this.tail
fields. This solution works even if this.tail
is not initialized. Moreover, if it is assigned beforehand, you don't need to iterate through the linked list from beginning.