Leetcode、牛客、PTA原题:“回文链表”和“合并有序
Leetcode、牛客、PTA原题:“回文链表”和“合并有序链表”
一、题目要求:回文链表
解题:
代码:
class Solution { public boolean isPalindrome(ListNode head) { ListNode p1 = replace(head); while(head != null && p1 != null){ // 存在不同值的节点时 if(head.val != p1.val){ return false; } head = head.next; p1 = p1.next; } return true; } // 反转链表 public ListNode replace(ListNode head){ // 创建一个新链表,n1为头指针先指向空 ListNode n1 = null; // 创建一个p节点,获取旧链表 ListNode p = head; // 遍历旧链表,当不为空说明还有下一节点 while (p != null){ // 使用头插入,将每次遍历到的节点插入到新链表头 n1 = new ListNode(p.val, n1); // 旧链表的下一节点 p = p.next; } // 返回新链表 return n1; } }
思路: 先将原链表==反转==,将反转后的链表与原链表进行逐一节点值的对比。反转链表的讲解请参考反转链表关键点: 在反转链表时,不可以使用递归算法进行链表的反转,因为使用链表的话,其实链表的地址是没有发生改变的。因此在比较时无法通过某些测试点。
二、题目要求:合并两个有序链表
题解:
代码:
class Solution { public ListNode mergeTwoLists(ListNode list1, ListNode list2) { // // 创建一个带有哨兵节点新的链表 // ListNode s = new ListNode(-1,null); // // 新链表的指针 // ListNode p = s; // // 判断两个链表的每个节点比较大小 // while(list1 != null && list2 != null){ // // list1<list2的情况 // if(list1.val < list2.val){ // // 将list1的节点值链接到新链表s // p.next = list1; // // 将list1往后移一位 // list1 = list1.next; // }else{ // // 同理 // p.next = list2; // list2 = list2.next; // } // // 将新链表添加成功一个节点后往后移一位 // p = p.next; // } // // 判断list1和list2那个链表先不为空,将剩下的链表接到新链表中 // if(list2 != null){ // p.next = list2; // } // if(list1 != null){ // p.next = list1; // } // // 返回带有哨兵节点的新链表 // return s.next; // 递归实现 if(list1 == null){ return list2; } if(list2 == null){ return list1; } if(list1.val < list2.val){ // 链表1往后移一位,继续与p2当前节点比较。并返回当前节点 list1.next = mergeTwoLists(list1.next,list2); return list1; }else{ list2.next = mergeTwoLists(list1,list2.next); return list2; } }
思路1:创建一个带有==指针p==和==哨兵节点==的新链表p,初始化状态时将s=null
,p = s
。对于链表l1和链表l2。首先:保证两个链表都未到==尾节点(null)==,对l1.val 与 l2.val进行比较
,若l1.val < l2.val
时,将l1.val连接到p
然后节点往后移一位。对于l1.val > l2.val
的情况也是同理处理即可。最后要对那个链==未空==进行确定,将==未空链表的剩下节点全部连接到p即可。
图解:
思路2: 递归实现递归实现时,无需创建新的链表。若l1.val < l2.val
,则递归让l1后移一位,但l2留在原地
。对于l1.val>l2.val
的情况只需要做相反操作即可。最后一步处理的是那个链表上的节点就将那个链表进行
返回即可得到合并后的链表
图解:
总结:
一开始对于回文链表使用==递归==反转链表后于原链表进行对比时,总是有一个测试点[1,1,2,1]
未通过,查看反转后的链表也确实反转过来了。一直搞不懂为什么会不通过。原来是递归后返回的链表==内存地址指向于原链表相同==在比较时并不是比较节点值,比较了节点的地址那当然一致了
。因此要使用新建链表的方式进行反转后再对比。
记录自己刷题的题解。坚持每天更新