/**
* 题目15:反转链表
* 输入一个链表,反转链表后,输出新链表的表头。
*/
@Test
public void test15(){
ListNode root=new ListNode(1);
ListNode tmp=root;
System.out.print("original List: "+root.val+"\t");
for(int i=2;i<6;i++){
tmp.next=new ListNode(i);
tmp=tmp.next;
System.out.print(tmp.val+"\t");
}
root=ReverseList_15_3(root);
System.out.print("\nreverse List: ");
while(root!=null){
System.out.print(root.val+"\t");
root=root.next;
}
}
//解法1:使用3个指针进行反转
//时间、空间复杂度O(n)、O(1) 22ms
public ListNode ReverseList_15(ListNode head) {
ListNode cur=head, pre=null ,next;
while(cur!=null){
next=cur.next;
cur.next=pre;
pre=cur;//pre往后移一位
cur=next;//cur往后移动一位
}
return pre;
}
//解法2:使用ArrayList来存储节点,然后遍历并反向 23ms
//或者直接使用栈进行逆序
public ListNode ReverseList_15_2(ListNode head) {
if(head==null || head.next==null) return head;
ArrayList<ListNode> arr=new ArrayList<>();//ctrl + alt + v自动补全左侧
while(head!=null) {
arr.add(head);
head=head.next;
}
arr.get(0).next=null;
for (int i = 1; i < arr.size(); i++) {
arr.get(i).next=arr.get(i-1);
}
return arr.get(arr.size()-1);
}
//解法3:递归进行逆序,时间复杂度O(n) 18ms
//将链表分为第一个节点head和剩余的节点rest,将剩余的节点rest反转,此时头指针rest指向原链表的末尾
//通过head.next找到逆序后rest的尾部节点,因此head.next.next=head即可完全逆序,头指针依旧是rest
public ListNode ReverseList_15_3(ListNode head) {
if(head==null || head.next==null) return head;
ListNode rest = ReverseList_15_3(head.next);
head.next.next = head;
head.next = null;
return rest;
}
京公网安备 11010502036488号