35_复杂链表的复制

package pers.lyt.java;

//题目 
//	请实现函数ComplexListNode* Clone(ComplexListNode* pHead),复制一个复杂链表。
//在复杂链表中,每个结点除了有一个m_pNext指针指向下一个点外,还有一个m_pSibling 指向
//链表中的任意结点或者nullptr。
//思路
//	思路1:先复制结点,用next链接,最后根据原始结点的sibling指针确定该sibling结点距离
//头结点的位置,从而对复制结点设置sibling指针。但是该思路对于n个结点的链表,每个结点的
//sibling都需要O(n)个时间步才能找到,所以时间复杂度为O(n^2)
//	思路2:复制原始结点N创建N’,用next链接。将<N,N'>的配对信息存放入一个哈希表中;
//在设置sibling时,通过哈希表,只需要用O(1)的时间即可找到复制结点的sibling。该方法的
//时间复杂度为O(n),但空间复杂度为O(n)。
//	思路3:复制原始结点N创建N’,将N'链接到N的后面;根据原始结点N的sibling可以快速设置N'
//结点的sibling,最后将这个长链表拆分成原始链表和复制链表(根据奇偶位置)
public class Offer35_CopyComplexList {
	public class ComplexListNode {
		int val;
		ComplexListNode next;
		ComplexListNode sibling;

		ComplexListNode(int val) {
			this.val = val;
		}
	}

	/*
	 * 主程序(包含三步)
	 */
	public ComplexListNode cloneList(ComplexListNode head) {
		cloneNodes(head); // 1.复制结点
		connectSiblingNodes(head); // 2.设置sibling
		return reconnectNodes(head);// 3.拆分长链表
	}

	/*
	 * 第一步:复制每个结点,并插入到原始节点的后面
	 */
	private void cloneNodes(ComplexListNode head) {
		ComplexListNode pNode = head;
		while (pNode != null) {
			ComplexListNode clonedNode = new ComplexListNode(pNode.val);
			clonedNode.next = pNode.next;
			pNode.next = clonedNode;
			pNode = clonedNode.next;
		}
	}

	/*
	 * 第二步:根据原结点的sibling,设置复制结点的sibling
	 */
	private void connectSiblingNodes(ComplexListNode head) {
		ComplexListNode pNode = head;
		while (pNode != null) {
			if (pNode.sibling != null) // 必须考虑到siblingNode==null的情况!
				pNode.next.sibling = pNode.sibling.next;
			pNode = pNode.next.next;
		}
	}

	/*
	 * 第三步:将长链表拆分成原始链表和复制链表(根据奇偶位置)
	 */
	private ComplexListNode reconnectNodes(ComplexListNode head) {
		ComplexListNode clonedHead = null;
		ComplexListNode clonedNode = null;
		ComplexListNode pNode = head;
		if (head != null) {
			clonedHead = head.next;
			clonedNode = pNode.next;
			pNode.next = clonedNode.next;
			pNode = pNode.next; // 提前将pNode指向下一个结点,方便判断是否为null
		}
		while (pNode != null) {
			clonedNode.next = pNode.next;
			clonedNode = clonedNode.next;
			pNode.next = clonedNode.next;
			pNode = pNode.next;
		}
		return clonedHead;
	}
	
//	第三步:简化版
//	private ComplexListNode reconnectNodes(ComplexListNode head) {
//		if(head == null)
//			return null;
//		ComplexListNode clonedHead = head.next;
//		ComplexListNode clonedNode = head.next;
//		ComplexListNode pNode = head;
//		while (clonedNode.next != null) {
//			pNode.next = clonedNode.next;
//			pNode = pNode.next;
//			clonedNode.next = pNode.next;
//			clonedNode = clonedNode.next;
//		}
//		return clonedHead;
//	}
	
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值