1.问题
给定链表 L0--L1--L2 ----L3 ---...... Ln,把链表重新排序为L0--Ln----L1---Ln-1----L2---Ln-2 。
要求: 1) 在原来链表的基础上排序,不能申请新的节点。
2)只能修改节点的next域,不能修改数据域。
2 思路分析:
1)首先找到链表的中间节点、
2)对链表的后半部分进行逆序
3)合并:分别从链表中各自取出一个节点,进行合并、
3 代码实现
package linkedlist.chongxinpailie;
public class TwoRealign {
public static void main(String[] args) {
int i=1;
LNode head=new LNode();
head.next=null;
LNode temp=null;
LNode cur=head;
//构造链表
for (;i<8;i++){
temp=new LNode();
temp.date=i;
temp.next=null;
cur.next=temp;
cur=temp;
}
System.out.print("排序前:");
for (cur=head.next;cur!=null;cur=cur.next){
System.out.print
(cur.date+" ");
}
Reorder(head);
System.out.println("排序后:");
for (cur=head.next;cur!=null;cur=cur.next){
System.out.print
(cur.date+" ");
}
}
/**
* 把链表从中间变成两个子链表
* @param head 头结点
* @return 返回链表的中间节点
*/
private static LNode FindMiddleNode(LNode head){
if (head==null||head.next==null){
return head;
}
LNode fast=head;//遍历链表时,每次前进两步
LNode slow=head;//遍历链表时,每次前进一步
LNode slowpre=head;
//这样的话,就是当fast遍历到链表尾部时,slow正好遍历到链表中间
while (fast!=null && fast.next!=null){//因为fast一次走两步,所以要fast!=null && fast.next!=null
slowpre=slow;//记录slow的位置
slow=slow.next;//后移一步
fast=fast.next.next;//后移两步
}
//把两个链表断开成两个独立的子链表
slowpre.next=null;
return slow;
}
/**
* 对不带头结点的链表进行反转
* @param head 链表头结点
* @return
*/
public static LNode Reverse(LNode head){
if (head==null||head.next==null){
return head;
}
LNode pre=head;//前驱结点
LNode cur=head.next;//当前节点
LNode next=null;//后继节点
pre.next=null;
//使遍历到的节点指向起前驱节点
while (cur!=null){
next=cur.next;//将当前节点的后一个节点暂存
cur.next=pre;//让当前的节点指向前驱节点
pre=cur;//pre后移
cur=cur.next;
cur=next;//当前节点后移
}
return pre;
}
/**
* 对链表进行拼接
* @param head 头结点
*/
public static void Reorder(LNode head){
if (head==null || head.next==null|| head.next.next==null){
return;
}
//前半部分链表的第一个节点
LNode cur1=head.next;
LNode mid = FindMiddleNode(head);
//后半段链表的第一个几点
LNode cur2 = Reverse(mid);
//辅助变量
LNode temp=null;
//合并两个链表
while (cur1.next!=null){
temp=cur1.next;//将cur1的后继节点保存起来
cur1.next=cur2;//令cur1 指向cur2
cur1=temp;//cur1后移
temp=cur2.next;
cur2.next=cur1;
cur2=temp;
}
cur1.next=cur2;
}
}
class LNode{
LNode next;
int date;
}