Leetcode Day1
leetcode -1 兩數之和
- 題目描述
给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出 和为目标值 的那 两个 整数,并返回它们的数组下标。
你可以假设每种输入只会对应一个答案。但是,数组中同一个元素不能使用两遍。
你可以按任意顺序返回答案。
- 解一
解題思路: 就是用兩個 for 循環遍歷數組,非常基礎。
/**
* @param {number[]} nums
* @param {number} target
* @return {number[]}
*/
let twoSum = function(nums, target) {
let res = [];
for(let i=0; i<nums.length; i++) {
for(let j=i+1; j<nums.length; j++) {
if(nums[i] + nums[j] == target){
res.push(i,j);
return res;
}
}
}
}
- 解二
解題思路: 哈希表
- 在遍歷的過程時,紀錄一些信息,省去一層 for(空間換時間)
- 紀錄已經遍歷過的數值和他的對應下標,方便查表
/**
* @param {number[]} nums
* @param {number} target
* @return {number[]}
*/
let twoSum = function(nums, target) {
let len = nums.length;
let map = new Map();
map.set(nums[0], 0);
for(let i=1; i<len; i++) {
let other = target - nums[i];
if(map.get(other) != undefined) {
return [map.get(other), i];
}
map.set(nums[i], i);
}
}
leetcode -2 兩數相加
- 題目描述
给你两个 非空 的链表,表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的,并且每个节点只能存储 一位 数字。
请你将两个数相加,并以相同形式返回一个表示和的链表。
你可以假设除了数字 0 之外,这两个数都不会以 0 开头。
- 解
/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} l1
* @param {ListNode} l2
* @return {ListNode}
*/
let addTwoNumbers = function(l1, l2) {
let p1 = l1;
let p2 = l2;
let carry = 0;
const dummy = new ListNode();
let pointer = dummy;
while(p1 || p2 || carry) {
const num1 = p1 ? p1.val : 0;
const num2 = p2 ? p2.val : 0;
const sum = num1 + num2 + carry;
if(sum > 9) {
pointer.next = new ListNode(sum%10);
carry = 1;
}else {
pointer.next = new ListNode(sum);
carry = 0;
}
if(p1) {
p1 = p1.next;
}
if(p2) {
p2 = p2.next;
}
pointer = pointer.next;
}
return dummy.next;
}
leetcode -3 無重複字符的最長子串
- 題目描述
给定一个字符串,请你找出其中不含有重复字符的 最长子串 的长度。
- 解一
解題思路: 用兩個 for 循環遍歷字符串,並用中間數組 tmp 紀錄已添加字符。但是這種方法要率很差,且有很多特殊用例會導致代碼有 bug。
/**
* @param {string} s
* @return {number}
*/
let lengthOfLongestSubstring = function(s) {
let len = s.length;
if(s == "")
return 0;
if(s == " ")
return 1;
if(len == 1)
return 1
let res = 0;
let tmp = [];
for(let i=0; i<len; i++) {
tmp.push(s[i]);
for(let j=i+1; j<len; j++) {
if(tmp.includes(s[j])) {
if(tmp.length > res) {
res = tmp.length;
}
break;
}else {
if(i==0 && j == len-1) {
return s.length;
}
tmp.push(s[j]);
if(j == len -1){
if(tmp.length > res) {
res = tmp.length;
}
}
}
}
tmp = [];
}
return res;
}
- 解二
解題思路: 其實這題要考的點是 滑動窗口。這邊使用到了 js 的 Set。通過一個 right 指針去滑動字符串窗口,並用 set 方便添加和刪除元素。
/**
* @param {string} s
* @return {number}
*/
let lengthOfLongestSubstring = function(s) {
let res = 0;
let right = 0;
const len = s.length;
let window = new Set();
for(let i=0; i<len; i++) {
while(right < len && !window.has(s.charAt(right))) {
window.add(s.charAt(right));
right++;
}
window.delete(s.charAt(i));
res = Math.max(res, right - i);
}
return res;
}