对于单链表相关的问题,双指针技巧是一种非常广泛且有效的解决方法。以下是一些常见问题以及使用双指针技巧解决
总的来说,双指针技巧在解决单链表相关问题时非常实用,它能够高效地解决许多常见问题,包括合并、分解、寻找节点、判断是否存在环等等。
将两个升序链表合并为一个新的 升序 链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。
示例 1:
输入:l1 = [1,2,4], l2 = [1,3,4]
输出:[1,1,2,3,4,4]
示例 2:
输入:l1 = [], l2 = []
输出:[]
示例 3:
输入:l1 = [], l2 = [0]
输出:[0]
提示:
[0, 50]
-100 <= Node.val <= 100
l1
和 l2
均按 非递减顺序 排列对两个链表进行比较,较小的再NewNode后面,NewNode向后移动;如果循环结束均为空,说明NewNode为合并后的链表;如果list1或list2其中一个为空,则NewNode连接的另一个链表就是合并后的链表
/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode() {}
* ListNode(int val) { this.val = val; }
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
* }
*/
class Solution {
public ListNode mergeTwoLists(ListNode list1, ListNode list2) {
//定义哨兵
ListNode NewNode=new ListNode(-1);
ListNode head=NewNode;
//对两个链表进行比较,较小的再NewNode后面,NewNode向后移动。
//如果循环结束均为空,说明NewNode为合并后的链表
//如果list1或list2其中一个为空,则NewNode连接的另一个链表就是合并后的链表
while(list1 != null && list2!=null){
if(list1.val <= list2.val){
NewNode.next=new ListNode(list1.val);
NewNode=NewNode.next;
list1=list1.next;
}else{
NewNode.next=new ListNode(list2.val);
NewNode=NewNode.next;
list2=list2.next;
}
}
if(list1==null && list2==null){
return head.next;
}else if(list1==null){
NewNode.next=list2;
}else{
NewNode.next=list1;
}
return head.next;
}
}
这是一道困难的题目,题目给出K给有序链表,我们应该使用更加高效的方法(优先队列)来解决。
给你一个链表数组,每个链表都已经按升序排列。请你将所有链表合并到一个升序链表中,返回合并后的链表。
示例 1:
输入:lists = [[1,4,5],[1,3,4],[2,6]]
输出:[1,1,2,3,4,4,5,6]
解释:链表数组如下:
[
1->4->5,
1->3->4,
2->6
]
将它们合并到一个有序链表中得到。
1->1->2->3->4->4->5->6
示例 2:
输入:lists = []
输出:[]
示例 3:
输入:lists = [[]]
输出:[]
提示:
k == lists.length
0 <= k <= 10^4
0 <= lists[i].length <= 500
-10^4 <= lists[i][j] <= 10^4
lists[i]
按 升序 排列lists[i].length
的总和不超过 10^4
/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode() {}
* ListNode(int val) { this.val = val; }
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
* }
*/
class Solution {
public ListNode mergeKLists(ListNode[] lists) {
if(lists.length==0)return null;
ListNode dump=new ListNode(-1);
ListNode result=dump;
//定义优先队列 二叉堆
PriorityQueue<ListNode> pql=new PriorityQueue<>(lists.length,(a,b)->(a.val-b.val));
//将每个链表的头节点加入二叉堆中
for(ListNode head:lists){
if(head!=null){
pql.add(head);
}
}
//如果队列不为空,取出优先队列的最小值,加入新链表中,再将最小值的下一节点加入优先队列中
while(!pql.isEmpty()){
ListNode temp=pql.poll();
dump.next=temp;
if(temp.next!=null){
pql.add(temp.next);
}
dump=dump.next;
}
return result.next;
}
}