两个链表数字相加

给出两个 非空 的链表用来表示两个非负的整数。其中,它们各自的位数是按照 逆序 的方式存储的,并>且它们的每个节点只能存储 一位 数字。
如果,我们将这两个数相加起来,则会返回一个新的链表来表示它们的和。
您可以假设除了数字 0 之外,这两个数都不会以 0 开头。

示例:
// 输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
// 输出:7 -> 0 -> 8
// 原因:342 + 465 = 807

  • 思路:从个位相加计算进位值和个位值拼接到链表next中
  • 时间复杂度:O(max(m,n))
  • 空间复杂度:O(\max(m,n))O(max(m,n))
fun addTwoNumbers(l1: ListNode?, l2: ListNode?): ListNode? {
        if (l1 == null || l2 == null) {
            return null
        }
        var temp1 = l1
        var temp2 = l2
        var carry = 0
        var resultNode: ListNode? = null
        var tempNode: ListNode? = null
        while (temp1 != null || temp2 != null) {
            val t1 = temp1?.`val` ?: 0
            val t2 = temp2?.`val` ?: 0
            val t12 = t1 + t2 + carry
            // 个位
            val bits = t12 % 10
            if (resultNode == null) {
                resultNode = ListNode(bits)
                tempNode = resultNode
            } else {
                val node = ListNode(bits)
                tempNode!!.next = node
                tempNode = node
            }
            // 进位
            carry = t12 / 10
            temp1 = temp1?.next
            temp2 = temp2?.next
            // 最后一次如果有进位
            if (carry > 0) {
                tempNode.next = ListNode(carry)
            }
        }
        return resultNode
    }
实现两个超大数相加,可以使用链表储这两个数。具体步骤如下: 1. 定义链表节点,包含一个值和指向下一个节点的指针。 ``` struct ListNode { int val; ListNode *next; ListNode(int x) : val(x), next(NULL) {} }; ``` 2. 将两个超大数分别储到两个链表中,每个节点储一位数字。 ``` ListNode *num1 = new ListNode(0); ListNode *num2 = new ListNode(0); ListNode *p1 = num1, *p2 = num2; for (int i = 0; i < len1; i++) { p1->val = num1_str[len1 - 1 - i] - '0'; if (i != len1 - 1) { p1->next = new ListNode(0); p1 = p1->next; } } for (int i = 0; i < len2; i++) { p2->val = num2_str[len2 - 1 - i] - '0'; if (i != len2 - 1) { p2->next = new ListNode(0); p2 = p2->next; } } ``` 其中,`num1_str`和`num2_str`为两个超大数的字符串表示,`len1`和`len2`为它们的长度。 3. 对两个链表进行遍历,依次相加每一位,并将结果储到新的链表中。 ``` ListNode *result = new ListNode(0); ListNode *p = result; int carry = 0; while (num1 || num2) { int sum = carry; if (num1) { sum += num1->val; num1 = num1->next; } if (num2) { sum += num2->val; num2 = num2->next; } p->val = sum % 10; carry = sum / 10; if (num1 || num2 || carry) { p->next = new ListNode(0); p = p->next; } } if (carry) { p->val = carry; } ``` 4. 将新的链表反转,得到相加后的结果。 ``` ListNode *rev_result = NULL; while (result) { ListNode *next = result->next; result->next = rev_result; rev_result = result; result = next; } ``` 最终,`rev_result`就是两个超大数相加的结果。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值