RecordList

1.借用的是堆栈,将其进行压入和压出模拟

 1 package LeetCode;
 2 import java.util.Stack;
 3 public class RecordList {
 4 
 5     public static  class ListNode
 6     {
 7         int val;
 8         ListNode next;
 9         
10         ListNode(int x) {
11                      val = x;
12                      next = null;
13                 }
14         
15     }
16     ListNode root;
17     
18     public RecordList(int array[])
19     {
20         /*直接建立链表*/
21         ListNode proot=new ListNode(array[0]);
22         ListNode r=proot;
23         for(int i=1;i<array.length;i++)
24         {
25             
26             r.next=new ListNode(array[i]);
27             r=r.next;
28         }
29         
30         root=proot;
31     }
32     public void recorderList( ListNode head)
33     {
34         if(head==null)
35             return ;
36         Stack<ListNode> st=new Stack<ListNode>();
37         
38         ListNode firstHead= head.next;
39         while(firstHead!=null)
40         {
41             st.push(firstHead);
42             firstHead=firstHead.next;
43         }
44         
45     
46         
47         ListNode pt=head.next;
48         ListNode newHead=new ListNode(head.val),p=newHead;
49         
50         int i=0;
51         
52          while(i<st.size())
53         {
54             p.next=st.peek();
55             st.pop();
56             p=p.next;
57             
58             p.next=pt;
59             p=p.next;
60             
61             pt=pt.next;
62             
63             i++;
64         }
65         p.next=null;
66         Print(newHead);
67     }
68     public void Print(ListNode h)
69     {
70         while(h!=null)
71         {
72             System.out.print(h.val+"-->");
73             h=h.next;
74             
75         }
76     }
77     public static void main(String[] args) {
78         
79         int [] array={1,2,3,4};
80         RecordList R=new RecordList(array);
81         R.recorderList(R.root);
82         
83         //System.out.print(array.length);
84         
85     }
86 }

2.如果不借用堆栈,由题意得recordList最后一个数字肯定是输入原来链表的中间点值,因此使用快慢链表的方式,将原来链表进行分割。

链表的反转和链表的连接;两部分合并

  1 package LeetCode;
  2 import java.util.Stack;
  3 public class RecordList {
  4 
  5     public static  class ListNode
  6     {
  7         int val;
  8         ListNode next;
  9         
 10         ListNode(int x) {
 11                      val = x;
 12                      next = null;
 13                 }
 14         
 15     }
 16     ListNode root;
 17     
 18     public RecordList(int array[])
 19     {
 20         /*直接建立链表*/
 21         ListNode proot=new ListNode(array[0]);
 22         ListNode r=proot;
 23         for(int i=1;i<array.length;i++)
 24         {
 25             
 26             r.next=new ListNode(array[i]);
 27             r=r.next;
 28         }
 29         
 30         root=proot;
 31     }
 32     public void recorderList( ListNode head)
 33     {
 34         if(head==null)
 35             return ;
 36         Stack<ListNode> st=new Stack<ListNode>();
 37         
 38         ListNode firstHead= head.next;
 39         while(firstHead!=null)
 40         {
 41             st.push(firstHead);
 42             firstHead=firstHead.next;
 43         }
 44         
 45     
 46         
 47         ListNode pt=head.next;
 48         ListNode newHead=new ListNode(head.val),p=newHead;
 49         
 50         int i=0;
 51         
 52          while(i<st.size())
 53         {
 54             p.next=st.peek();
 55             st.pop();
 56             p=p.next;
 57             
 58             p.next=pt;
 59             p=p.next;
 60             
 61             pt=pt.next;
 62             
 63             i++;
 64         }
 65         p.next=null;
 66         Print(newHead);
 67     }
 68     public void Print(ListNode h)
 69     {
 70         while(h!=null)
 71         {
 72             System.out.print(h.val+"-->");
 73             h=h.next;
 74             
 75         }
 76     }
 77     public static void main(String[] args) {
 78         
 79         int [] array={1,2,3,4,5};
 80         RecordList R=new RecordList(array);
 81         //R.recorderList(R.root);
 82         R.recordlist(R.root);
 83         //System.out.print(array.length);
 84         
 85     }
 86     
 87     /*只能在本链表上运转,不能使用stack等数据链表
 88      *  只能使用快慢指针*/
 89     
 90     public void recordlist(ListNode head)
 91     {
 92         if(head==null || head.next==null)
 93             return;
 94         
 95         ListNode fast=head,slow=head;
 96         
 97         while(fast.next!=null && fast.next.next!=null)
 98         {
 99             fast=fast.next.next;
100             slow=slow.next;
101         }
102         /*将链表从中隔离,同时将中点之后的链表进行反转,最后再将其进行连接*/
103         ListNode f=reverse(slow.next);//此时fast节点已经发生反转
104         
105         merge(head,slow,f);
106     }
107     
108     public void merge(ListNode head,ListNode end1,ListNode head2)
109     {
110         ListNode pt=head,head1=head;
111         while(head1!=end1)
112         {
113             head1=head1.next;
114             
115             pt.next=head2;
116             pt=pt.next;//记着指针要移动
117             
118             head2=head2.next;
119             
120             
121             pt.next=head1;
122             pt=pt.next;
123         }
124         pt.next=null;
125         
126         Print(head);
127     }
128     public ListNode reverse(ListNode head)
129     {
130         /*主要讲链表进行反转*/
131         int i=0;
132         ListNode pre=head,
133         cur=head.next,temp;
134         /*在自身上进行链表反转*/
135         while(cur!=null)
136         {
137             temp=cur.next; //原链表下一个节点进行保存
138             //将pre连接到当前节点上
139             cur.next=pre;
140             
141             //链表向前移动
142             pre=cur;
143             cur=temp;
144             ++i;
145         }
146         //得到会形成循环链表
147         ListNode h=pre;
148         while(i-->0)
149         {
150             h=h.next;
151         }
152         h.next=null;
153         return pre;
154     }
155 }

 2.如果不采用指针形式,采用链表自身反转和链表的合并:

1.链表的反转过程中解析:采用链表的循环反转,1-2-3-4  --->2-1-3-4 --->3-2-1-4----->4-3-2-1 pre指针始终指向节点1,将节点1.next移动的链表首部

具体做法:让头结点的。next指向2节点2,让节点1的next指向结点3(保存结点不丢失)最后将结点1连接到结点2后面 2-1-3-4.

同样p1结点总是指向结点1,同样操作,让head。next=结点1的。next

 1 public static void reverse(ListNode head)
 2     {
 3         ListNode p1=head;
 4         ListNode p2=head.next;
 5         
 6         while(p2.next!=null)
 7         {
 8             /*相当于将节点单独的剥离出来*/
 9             ListNode current=p2.next;
10             p2.next=current.next;
11             
12             current.next=head.next;/*注意 不能连接 p2,因为p2后面连接的结点不断地变化,最终会让
13                                      翻转链表树减少*/
14             p1.next=current;
15         }
16     }

在链表中某一部分进行翻转

 1 ListNode p11=head.next,p22=slow.next;
 2         //循环链表方式
 3         
 4         while(p11.next!=p22)
 5         {
 6             ListNode current=p11.next;
 7             p11.next=current.next;
 8             
 9             current.next=head.next;
10             head.next=current;
11             Print(head);
12         }
原始序列 1-2-3-4-5-6-7-8 
1-->3-->2-->4-->5-->6-->7-->8--> 1-->4-->3-->2-->5-->6-->7-->8-->

即使 1-2-3-4,
1-->4-->3-->2-->

最后进行逐一reorder时候 1-2-3-4-8-7-6-5;将结点8连接到head。next同时 2连接到8.next  1-8-2-3-4-7-6-5 完成一次循环后将指针指向结点2,另外一个指针指向prmid.next 相当于将链表进行

不断地reorder。

 1 public static void reorder(ListNode newhead,ListNode premid)
 2     {
 3         ListNode p1=newhead;
 4         ListNode p2=premid.next;
 5         
 6         while(p1!=premid)
 7         {
 8             //将连接链表进行剥离
 9             premid.next=p2.next;
10             p2.next=p1.next;
11             p1.next=p2;
12             
13             p1=p2.next;
14             p2=premid.next;
15         }
16         
17     }
 1 
原文地址:https://www.cnblogs.com/woainifanfan/p/6511943.html