问题描述:https://leetcode.com/problems/add-two-numbers/

思路1:基本加法规则

根据小学学的基本加法规则。。。。。我们需要将两个数以最低位为基准对齐,然后逐个加,需要进位的给进位就行了。。。。恰好这个链表是逆序的!!!已经为我们对齐了。用两个指针分别指向两个链表头,开始同步往后移动,边移动边计算结果,直到两个指针都到了尽头/没有进位。时间复杂度是O(max(m, n)),空间复杂度和时间复杂度一样。js代码如下:

// Runtime: 116 ms
var addTwoNumbers = function(l1, l2) {
let dummy = { next: null }, // 结果链表的head指针
tail = dummy, // tail总是指向dummy的末尾元素,以便在链表尾插入新元素
flag = false, // flag标示是否需要进位
sum; let init = () => { // 初始化,因为保证非空,所以首位总是存在的(可能为0)
sum = l1.val + l2.val;
tail.next = new ListNode(sum % 10);
// 为下一位的计算做准备
flag = sum >= 10;
l1 = l1.next;
l2 = l2.next;
// 保持tail性质不变
tail = tail.next;
}; let work = () => {
let v1, v2;
while (l1 || l2 || flag) {
// 统一化处理,不用判断谁空谁不空
v1 = l1 ? l1.val : 0;
v2 = l2 ? l2.val : 0;
sum = v1 + v2 + (flag ? 1 : 0);
tail.next = new ListNode(sum % 10);
// 为下一位的计算做准备
flag = sum >= 10;
l1 = l1 ? l1.next : null;
l2 = l2 ? l2.next : null;
// 保持tail性质不变
tail = tail.next;
}
}; init();
work(); return dummy.next;
};
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* addTwoNumbers(struct ListNode* l1, struct ListNode* l2) {
struct ListNode *l3 = malloc(sizeof(struct ListNode));
struct ListNode *tail = l3; int sum = l1->val + l2->val;
tail->val = sum % ;
int flag = sum >= ;
l1 = l1->next;
l2 = l2->next; int v1, v2;
while (l1 || l2 || flag) {
v1 = l1 ? l1->val : ;
v2 = l2 ? l2->val : ;
sum = v1 + v2 + (flag ? : ); tail->next = malloc(sizeof(struct ListNode));
tail = tail->next;
tail->val = sum % ; flag = sum >= ;
l1 = l1 ? l1->next : NULL;
l2 = l2 ? l2->next : NULL;
} tail->next = NULL; // 这句话是必要的!否则提交后会有运行时错误。
return l3;
}

C语言版本

/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) { val = x; }
* }
*/
class Solution {
public ListNode addTwoNumbers(ListNode l1, ListNode l2) {
ListNode ans = new ListNode(0), tail = ans;
boolean flag = false; // 当前位是否需要进位
// 保持一个循环不变式:
// ans的前面n位为l1与l2前n位相加的正确结果
// l1与l2要么为空要么指向当前/即将计算位 // 初始化
int sum = l1.val + l2.val + (flag ? 1 : 0);
tail.val = sum % 10; flag = sum >= 10;
l1 = l1.next;
l2 = l2.next; // 保持
int v1, v2; // l1.val与l2.val不能再直接用,可能为空
while (flag || l1 != null || l2 != null) {
if (l1 == null) {
v1 = 0;
} else {
v1 = l1.val;
l1 = l1.next;
} if (l2 == null) {
v2 = 0;
} else {
v2 = l2.val;
l2 = l2.next;
} sum = v1 + v2 + (flag ? 1 : 0);
tail.next = new ListNode(sum % 10); flag = sum >= 10;
tail = tail.next;
} // 终止 return ans;
}
}

Java版本

思路2:移花接木法。。。

基本上和思路1没区别,并不能改善时间复杂度的渐进性,只是省了点空间。js代码:

// 不创建新链表,直接把结果存到l1上,并对多出来的部分做"嫁接"处理
// Runtime: 112 ms, faster than 99.52% of JavaScript online submissions for Add Two Numbers.
var addTwoNumbers2 = function(l1, l2) {
let dummy = { next: l1 }, // 结果链表的head指针
tail = dummy, // tail总是指向l1的前继元素(也就是dummy的尾元素),以便在链尾插入链表/新元素
flag = false, // flag标示下一位的计算是否需要进位
sum; let init = () => { // 初始化,因为保证非空,所以首位总是存在的
sum = l1.val + l2.val;
l1.val = sum % 10;
// 为下一位的计算做准备
flag = sum >= 10;
l1 = l1.next;
l2 = l2.next;
// 保持tail性质不变
tail = tail.next;
}; let status1 = () => { // 处理等长的那部分
while (l1 && l2) {
sum = l1.val + l2.val + (flag ? 1 : 0);
l1.val = sum % 10;
// 为下一位的计算做准备
flag = sum >= 10;
l1 = l1.next;
l2 = l2.next;
// 保持tail性质不变
tail = tail.next;
}
}; let status2 = () => { // 处理多出来的部分
// 如果l2更长,直接移植到l1
if (l2) {
l1 = tail.next = l2;
}
// 处理进位
while (l1 && flag) {
sum = l1.val + 1;
l1.val = sum % 10;
// 为下一位的计算做准备
flag = sum >= 10;
l1 = l1.next;
// 保持tail性质不变
tail = tail.next;
}
if (flag) {
tail.next = new ListNode(1);
}
}; init();
status1();
status2(); return dummy.next;
};

LeetCode #002# Add Two Numbers(js描述)的更多相关文章

  1. 【JAVA、C++】LeetCode 002 Add Two Numbers

    You are given two linked lists representing two non-negative numbers. The digits are stored in rever ...

  2. [Leetcode] 002. Add Two Numbers

    https://leetcode.com/problems/add-two-numbers/ public class Solution { public ListNode addTwoNumbers ...

  3. LeetCode:1. Add Two Numbers

    题目: LeetCode:1. Add Two Numbers 描述: Given an array of integers, return indices of the two numbers su ...

  4. LeetCode(2) || Add Two Numbers && Longest Substring Without Repeating Characters

    LeetCode(2) || Add Two Numbers && Longest Substring Without Repeating Characters 题记 刷LeetCod ...

  5. [LeetCode] 445. Add Two Numbers II 两个数字相加之二

    You are given two linked lists representing two non-negative numbers. The most significant digit com ...

  6. [Leetcode Week15] Add Two Numbers

    Add Two Numbers 题解 原创文章,拒绝转载 题目来源:https://leetcode.com/problems/add-two-numbers/description/ Descrip ...

  7. LeetCode 面试:Add Two Numbers

    1 题目 You are given two linked lists representing two non-negative numbers. The digits are stored in ...

  8. [LeetCode] 2. Add Two Numbers 两个数字相加 java语言实现 C++语言实现

    [LeetCode] Add Two Numbers 两个数字相加   You are given two non-empty linked lists representing two non-ne ...

  9. [LeetCode] 2. Add Two Numbers 两个数字相加

    You are given two non-empty linked lists representing two non-negative integers. The digits are stor ...

随机推荐

  1. CocoaPods 添加WebP失败解决办法

    pod 'sdwebimage/webp' 下载libwebp 超时 [!] Error installing libwebp [!] /usr/bin/git clone https://chrom ...

  2. OpenGL——OpenCV与SOIL读取图片进行纹理贴图

    使用OpenCV读取图片代码如下 img = imread(m_fileName); if (img.empty()) { fprintf(stderr, "Can not load ima ...

  3. nginx配置-为没有后缀的文件(实际上是有html文件)以html形式打开

    location ~ index.php@ { add_header content-type "text/html"; }

  4. react useRef()函数

    "ref"对象是一个通用容器,其current属性是可变的 保存dom function Test() { const t = useRef(null); useEffect(() ...

  5. 原生 JavaScript 实现 state 状态管理系统

    原生 JavaScript 实现 state 状态管理系统 Build a state management system with vanilla JavaScript | CSS-Tricks 在 ...

  6. C#在WinForm下使用HttpWebRequest上传文件

    转自:http://blog.csdn.net/shihuan10430049/article/details/3734398 这段时间因项目需要,要实现WinForm下的文件上传,个人觉得采用FTP ...

  7. ELK之使用heartbeat监控WEB站点

    简介 无论您要测试同一台主机上的服务,还是要测试开放网络上的服务,Heartbeat 都能轻松生成运行时间数据和响应时间数据 Heartbeat 能够通过 ICMP.TCP 和 HTTP 进行 pin ...

  8. Centos7.1环境下搭建BugFree

    环境准备: 系统 配置 IP Centos7.1 1核2G+60GB硬盘 10.10.28.204 1. 安装apache yum install httpd  2. 安装mysql yum inst ...

  9. java框架之Struts2(1)-简介及入门

    简介 Struts2 是一个基于 MVC 设计模式的 Web 应用框架,它本质上相当于一个 servlet,在 MVC 设计模式中,Struts2 作为控制器 (Controller) 来建立模型与视 ...

  10. freeswitch报错

    1.         2010-10-26 11:01:58.448513 [ERR] sofia_reg.c:816 Can not do authorization without a compl ...