Skip to main content

Algorithm 算法

展开/收起分类
随机全部
顺序全部
随机置顶
随机 🍀
顺序 🍀
5道(24
随机 ⚡️
重置
1

一般算法

查找句子频率出现最高的单词

const article = "This is a pen, a pencil.";

const findMostWord = (article) => {
// ...
}

findMostWord(article) // ['a', 2]

小孩报数(约瑟夫环)问题

// 有 30 个小孩,编号从 1 到 30,围成一圈依次报数 1、2、3
// 数到 3 的小孩儿退出这个圈,然后下一个小孩重新报数 1、2、3
// 问最后剩下的那个小孩儿的编号是多少?

【LC】20. 有效的括号

https://leetcode.cn/problems/valid-parentheses/

输入:s = "()"
输出:true

输入:s = "()[]{}"
输出:true

输入:s = "(]"
输出:false

/**
* @param {string} s
* @return {boolean}
*/
var isValid = function (s) {
// ...
};

【LC】76. 最小覆盖子串

https://leetcode.cn/problems/minimum-window-substring/

输入:s = "ADOBECODEBANC", t = "ABC"
输出:"BANC"
解释:最小覆盖子串 "BANC" 包含来自字符串 t 的 'A''B''C'

/**
* @param {string} s
* @param {string} t
* @return {string}
*/
var minWindow = function (s, t) {
const arr = s.split('')

};

【LC】347. 前 K 个高频元素

https://leetcode.cn/problems/top-k-frequent-elements/

输入: nums = [1,1,1,2,2,3], k = 2
输出: [1,2]

输入: nums = [1], k = 1
输出: [1]

/**
* @param {number[]} nums
* @param {number} k
* @return {number[]}
*/
var topKFrequent = function (nums, k) {
// ...
};

【LC】374. 猜数字大小

https://leetcode.cn/problems/guess-number-higher-or-lower/

输入:n = 10
输出:6

// 每轮游戏,我都会从 1 到 n 随机选择一个数字。 请你猜选出的是哪个数字。
// 如果你猜错了,我会告诉你,你猜测的数字比我选出的数字是大了还是小了。
// 提供一个 guess 方法,返回值如下:
// -1:我选出的数字比你猜的数字小 pick < num
// 1:我选出的数字比你猜的数字大 pick > num
// 0:我选出的数字和你猜的数字一样。恭喜!你猜对了!pick == num

/**
* Forward declaration of guess API.
* @param {number} num your guess
* @return -1 if num is higher than the picked number
* 1 if num is lower than the picked number
* otherwise return 0
* var guess = function(num) {}
*/

/**
* @param {number} n
* @return {number}
*/
var guessNumber = function (n) {
// ...
};

两两相加且不重复

给出一个数组,以及一个值。求数组中 两两相加的和等于该值的集合 有多少个?(如 8 + 1 与 1 + 8 重复,只记一次)

const arr = [1, 3, 8, 6, 1];  
fn(arr, 9); // 返回2(符合条件:1+8、3+6)
fn(arr, 4); // 返回1(符合条件:1+3)
fn(arr, 5); // 返回0(无符合条件的组合)

链表系列

【LC】237. 删除链表中的节点

https://leetcode.cn/problems/delete-node-in-a-linked-list/

输入:head = [4,5,1,9], node = 5
输出:[4,1,9]
解释:指定删除节点 5,调用后链表应变为 4 -> 1 -> 9

/**
* Definition for singly-linked list.
* function ListNode(val) {
* this.val = val;
* this.next = null;
* }
*/
/**
* @param {ListNode} node
* @return {void} Do not return anything, modify node in-place instead.
*/
var deleteNode = function (node) {
// ...
};

【LC】206. 反转链表

https://leetcode.cn/problems/reverse-linked-list/

输入:head = [1,2,3,4,5]
输出:[5,4,3,2,1]

输入:head = []
输出:[]

/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} head
* @return {ListNode}
*/
var reverseList = function (head) {
// ...
};

【LC】2. 两数相加

https://leetcode.cn/problems/add-two-numbers/

输入:l1 = [2,4,3], l2 = [5,6,4]
输出:[7,0,8]
解释:342 + 465 = 807

/**
* 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}
*/
var addTwoNumbers = function (l1, l2) {
// ...
};

【LC】83. 删除排序链表中的重复元素

https://leetcode.cn/problems/remove-duplicates-from-sorted-list/

输入:head = [1,1,2,3,3]
输出:[1,2,3]

/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} head
* @return {ListNode}
*/
var deleteDuplicates = function (head) {
// ...
};

【LC】141. 环形链表

https://leetcode.cn/problems/linked-list-cycle/

输入:head = [3,2,0,-4], pos = 1
输出:true
解释:链表中有一个环,其尾部连接到第二个节点。

输入:head = [1], pos = -1
输出:false
解释:链表中没有环。

/**
* Definition for singly-linked list.
* function ListNode(val) {
* this.val = val;
* this.next = null;
* }
*/

/**
* @param {ListNode} head
* @return {boolean}
*/
var hasCycle = function (head) {
// ...
};

【LC】21. 合并两个有序链表

https://leetcode.cn/problems/merge-two-sorted-lists/

输入:l1 = [1,2,4], l2 = [1,3,4]
输出:[1,1,2,3,4,4]

/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} list1
* @param {ListNode} list2
* @return {ListNode}
*/
var mergeTwoLists = function (list1, list2) {
// ...
};

【LC】23. 合并 K 个升序链表

https://leetcode.cn/problems/merge-k-sorted-lists/

输入:lists = [[1,4,5],[1,3,4],[2,6]]
输出:[1,1,2,3,4,4,5,6]
解释:链表数组如下:
[
1->4->5,
1->3->4,
2->6
]
将它们合并到一个有序链表中得到。
1->1->2->3->4->4->5->6

/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode[]} lists
* @return {ListNode}
*/
var mergeKLists = function (lists) {
// ...
};

二叉树系列

DFS 和 BFS 的区别,手写 DFS 和 BFS(ing)

深度优先遍历是尽可能深的搜索树的分支,而广度优先遍历是先访问根节点最近的节点。

const dfs = root => {
console.log(root.val)
root.children.forEach(dfs)
}
dfs(tree)

const bfs = root => {
const queue = []
if (root) queue.push(root)
while (queue.length) {
const curNode = queue.shift()
console.log(curNode.val)
curNode.children.forEach(child => {
queue.push(child)
})
}
}
bfs(tree)

二叉树前 / 中 / 后 / 层序遍历结果

上面二叉树先///层序遍历的结果为?

【LC】144. 二叉树的前序遍历(两种解法)

https://leetcode.cn/problems/binary-tree-preorder-traversal/

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/

/**
* @param {TreeNode} root
* @return {number[]}
*/
const preorderTraversal = (root) => {
// ...
};

【LC】94. 二叉树的中序遍历(两种解法)

https://leetcode.cn/problems/binary-tree-inorder-traversal/

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/

/**
* @param {TreeNode} root
* @return {number[]}
*/
const inorderTraversal = function (root) {
// ...
};

【LC】145. 二叉树的后序遍历(两种解法)

https://leetcode.cn/problems/binary-tree-postorder-traversal/

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/

/**
* @param {TreeNode} root
* @return {number[]}
*/
const postorderTraversal = function (root) {
// ...
};

【LC】102. 二叉树的层序遍历

https://leetcode.cn/problems/binary-tree-level-order-traversal/

    3
/ \
9 20
/ \
15 7

输入:root = [3, 9, 20, null, null, 15, 7]
输出:[[3], [9, 20], [15, 7]]

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number[][]}
*/
const levelOrder = function (root) {
// ...
};

【LC】104. 二叉树的最大深度

https://leetcode.cn/problems/maximum-depth-of-binary-tree/

    3
/ \
9 20
/ \
15 7

输入:root = [3, 9, 20, null, null, 15, 7]
输出:3

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var maxDepth = function (root) {
// ...
};

【LC】111. 二叉树的最小深度

https://leetcode.cn/problems/minimum-depth-of-binary-tree/

最小深度是从根节点到最近叶子节点(没有子节点的节点)的最短路径上的节点数。

    3
/ \
9 20
/ \
15 7

输入:root = [3, 9, 20, null, null, 15, 7]
输出:2

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var minDepth = function (root) {
// ...
};

【LC】112. 路径总和

https://leetcode.cn/problems/path-sum/

      5
/ \
4 8
/ / \
11 13 4
/ \ \
7 2 1

输入:root = [5,4,8,11,null,13,4,7,2,null,null,null,1], targetSum = 22
输出:true

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @param {number} targetSum
* @return {boolean}
*/
var hasPathSum = function (root, targetSum) {
// ...
};

计算二叉树的深度

某公司组织架构以二叉树形式记录,请返回该公司的层级数(即二叉树的最大深度,定义为根节点到最远叶子节点的最长路径上的节点数)。

   1
2 2
3 5
4 4

输出示例:

  • 输入root = [1,2,2,3,null,null,5,4,null,null,4](二叉树的数组表示,遵循层序遍历规则,null 代表空节点)
  • 输出4
  • 解释:最长路径为 1→2→3→41→2→5→4,路径包含 4 个节点,因此层级数为 4。

解法:

/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var maxDepth = function(root) {
// 空节点的深度为 0
if (root === null) {
return 0;
}
// 递归计算左子树的深度
const leftDepth = maxDepth(root.left);
// 递归计算右子树的深度
const rightDepth = maxDepth(root.right);
// 当前节点的深度 = 左右子树深度的最大值 + 1(自身)
return Math.max(leftDepth, rightDepth) + 1;
};