leetcode_7.合并两个有序链表

  • 合并两个有序链表:将两个有序链表合并为一个新的有序链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。
示例:
输入:1->2->4, 1->3->4
输出:1->1->2->3->4->4

一.递归法:

  • 首先处理链表 l1和 l2是否为空的情况

  • 因为l1和l2是有序链表,比较它们的第一个数,若l1<l2,则递归调用merge函数传入后续的l1->next,并返回此时比较后的最小结点l1;若l1>=2,则递归调用merge函数传入后续的l2->next,并返回此时比较后的最小结点l2;

  • 递归的终点为:
    if(l1= =NULL) return l2;
    if(l2= =NULL) return l1;

  • 做这个题发现可以直接:

 ListNode* p;    
 //等同于struct ListNode* p;
 p=(ListNode*)malloc(sizeof(ListNode)); 
 //等同于 p=(struct ListNode*)malloc(sizeof(struct ListNode)); 
  • 另外我觉得解决问题采用递归的方式挺难的,一是步骤抽象起来难,二是真正理解也难,可能我现在的能力还达不到。
  • 写这个题也让我知道了以前学的东西不一定完全弄懂了,一个知识点里面有许多的小细节,比如我将它搬到了devc中完整的实现,我需要创建并添加两个链表l1和l2的实例,我觉得当时我的链表学的还是挺好的,突然一写不知道怎么创建链表并链接起来了。最近写博客写的还是挺快的,目前来说记忆的还不够牢固和深入,我需要时常使用学过的知识并注意。
/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}  //类似类的构造函数,参数val和next的默认参数为传入的x和NULL
 * };
 */
class Solution {
    public:
     ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) 
     {
        if(l1==NULL) return l2;
        if(l2==NULL) return l1;
        if(l1->val < l2->val)
        {
            l1->next = mergeTwoLists(l1->next,l2);
            return l1;
        }
        else
        {
            l2->next = mergeTwoLists(l1,l2->next);
            return l2;
        }
     }
};

二.迭代法:

  • 思路倒是很简单,两个指针p1和p2是遍历两个有序链表的工具。若p1->val < p2->val,继续顺序往有序链表l1里找,直到大于则将两个链表通过指针将结点链接起来,改变对应信息,再继续比较直到p2为空。这里直接画个图解释其中的过程:
  • 怎么样,是不是思路很简单…这是我最近学算法和数据结构最大的感受,想法不是很难,但是实现起来倒是挺难。
  • 指针的路还需要磨练。
class Solution {
    public:
     ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
        if (l2 == NULL) return l1;
        if (l1 == NULL) return l2;
        ListNode* p1 = l1;  //p1可以访问到l1
        ListNode* p2 = l2;  //p2可以访问到l2
        ListNode* start = l1->val < l2->val ? l1 : l2;  //start指向两个有序链表中第一个结点较小的一个
        do {
            if (p1->val < p2->val)  //向p1链表中顺序往后遍历
            {
                while (p1->next != NULL && p1->next->val < p2->val)
                { 
                    p1 = p1->next; //若还是小于,则继续遍历直到不小于
                }
                l2 = p2->next;
                p2->next = p1->next;
                p1->next = p2;    //将p2指向的l2与p1衔接上
            } 
            else                  //向p2链表中顺序往后遍历
            {
                while (p2->next != NULL && p2->next->val <= p1->val)
                {
                    p2 = p2->next;
                }
                l2 = p2->next;
                p2->next = p1;
            }
            p2 = l2;
        }while (p2 != NULL);
        return start;
     }
};
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值