代码随想录算法训练营Day04 | 24.两两交换链表中的节点、19.删除链表的倒数第N个节点、160.链表相交、142.环形链表II

58 阅读1分钟

LeetCode题目

24.两两交换链表中的节点

题目链接:Swap Nodes in Pairs - LeetCode

代码如下:

func swapPairs(head *ListNode) *ListNode {
	// 创建虚拟头节点,虚拟头节点虽然被称为虚拟,但其真实存在于内存空间,只是不计入链表
	dummyHead := &ListNode{Val: 0, Next: head}
	cur := dummyHead
	for cur.Next != nil && cur.Next.Next != nil {
		tmp_1 := cur.Next
		tmp_2 := cur.Next.Next.Next
		cur.Next = cur.Next.Next
		cur.Next.Next = tmp_1
		cur.Next.Next.Next = tmp_2
		cur = cur.Next.Next
	}
	return dummyHead.Next
}

19.删除链表的倒数第N个节点

题目链接:Remove Nth Node From End of List - LeetCode

双指针法

代码如下:

func removeNthFromEnd(head *ListNode, n int) *ListNode {
	dummyHead := &ListNode{Val: 0, Next: head}
	fast, slow := dummyHead, dummyHead
	for i := 0; i < n+1; i++ {
		fast = fast.Next
	}
	for fast != nil {
		fast = fast.Next
		slow = slow.Next
	}
	slow.Next = slow.Next.Next
	return dummyHead.Next
}

另一种解法

倒数第N个节点的索引为 len - n ,即删除索引为 len - n 的节点

代码如下:

func getLength(head *ListNode) int {
	length := 0
	for head != nil {
		length++
		head = head.Next
	}
	return length
}

func removeNthFromEnd(head *ListNode, n int) *ListNode {
	dummyHead := &ListNode{Val: 0, Next: head}
	cur := dummyHead
	for i := 0; i < getLength(head)-n; i++ {
		cur = cur.Next
	}
	cur.Next = cur.Next.Next
	return dummyHead.Next
}

160.链表相交

题目链接:Intersection of Two Linked Lists - LeetCode

双指针法

代码如下:

func getIntersectionNode(headA, headB *ListNode) *ListNode {
	curA, curB := headA, headB
	for curA != curB {
		if curA != nil {
			curA = curA.Next
		} else {
			curA = headB
		}

		if curB != nil {
			curB = curB.Next
		} else {
			curB = headA
		}
	}

	return curA
}

另一种解法

代码如下:

func getIntersectionNode(headA, headB *ListNode) *ListNode {
	curA, curB := headA, headB
	lenA, lenB := 0, 0
	for curA != nil {
		lenA++
		curA = curA.Next
	}
	for curB != nil {
		lenB++
		curB = curB.Next
	}
	curA, curB = headA, headB
	if lenA > lenB {
		for i := 0; i < lenA-lenB; i++ {
			curA = curA.Next
		}
	} else {
		for i := 0; i < lenB-lenA; i++ {
			curB = curB.Next
		}
	}
	for curA != curB {
		curA = curA.Next
		curB = curB.Next
	}
	return curA
}

142.环形链表II

题目链接:Linked List Cycle II - LeetCode

代码如下:

func detectCycle(head *ListNode) *ListNode {
	fast, slow := head, head
	for fast != nil && fast.Next != nil {
		slow = slow.Next
		fast = fast.Next.Next
		if slow == fast {
			index1, index2 := fast, head
			for index1 != index2 {
				index1 = index1.Next
				index2 = index2.Next
			}
			return index2
		}
	}
	return nil
}

总结

  1. 链表中也经常用到双指针