说明
这个代码仓库是我在学习《算法与数据结构》的时候,在 LeetCode 上做的练习,这里是对应的 Java 仓库的地址。
建议您安装 Octotree 插件,以获得最佳的使用体验。
题目根据类别放在不同的文件夹下,方便自己复习和以后使用。
所有的代码都是通过 LeetCode 在线测评系统检测的,至少是正确的代码,但不一定是时间复杂度和空间复杂度最优的。
代码编写风格
在代码编写的过程中,我比较注意的地方有:
- 保证语义清晰,这一点我认为是最重要的。代码虽然是运行在机器上,但更多时候是写给人看的,在逻辑正确,时间复杂度和空间复杂度都较优的前提下,语义清晰的代码更便于他人理解,也更利于不同观点的人之间的沟通。不以追求代码最短为目标,有时为了分割语义,我还会加上空格,体现逻辑的层次。代码也不是在纸上写,没有必要节约代码空间,这意义不大;
- 变量和方法的命名尽量有意义,并且是见名知义的;
- Python 相比 Java 而言,语法比较灵活,可能会有一些比较 pythonista 的写法,让你的代码更简短更“好”,但刷题这件事情,应该更注重于常用算法数据结构和思想的应用,而少用例如 Python 这种有一些高度封装过后的代码库,相对而言 Java 和 C++ 更适合刷题。我工作以后,先会的 Java ,然后才会 Python,在 Python 中有 Java 中没有的语法,我就不会在刷题中用了;
- 所有的代码在提交到 LeetCode 在线测评系统之前,都使用了 PyCharm 提供的自动格式化功能(快捷键:alt + command + L),有些还使用了 autopep8 工具进行格式化,我个人还是比较看重代码颜值的,况且这样做成本也很低;
- 为了保证易读性,编码的时候会写上注释,有时注释甚至是啰嗦且多余的,还有一点,我怕以后自己再看的时候都看不懂当初是怎么写的。
对于一些比较经典的问题,我还写了题解,制作了动画,可以在以下的链接中找到。
刷题过程中在 LeetCode 中文版提交的题解和动画
LeetCode 第 23 题:合并 K 个排序链表
题解地址:https://leetcode-cn.com/problems/merge-k-sorted-lists/solution/tan-xin-suan-fa-you-xian-dui-lie-fen-zhi-fa-python/。
LeetCode 第 41 题:缺失的第一个正数
题解地址:https://leetcode-cn.com/problems/first-missing-positive/solution/tong-pai-xu-python-dai-ma-by-liweiwei1419/。
LeetCode 第 60 题:第 k 个排列
题解地址:https://leetcode-cn.com/problems/permutation-sequence/solution/hui-su-jian-zhi-python-dai-ma-java-dai-ma-by-liwei/。
LeetCode 第 148 题:单链表自底向上的“归并排序”
题解地址:https://leetcode-cn.com/problems/sort-list/solution/zi-di-xiang-shang-de-gui-bing-pai-xu-java-dai-ma-b/。
LeetCode 第 287 题:寻找重复数
题解地址:https://leetcode-cn.com/problems/find-the-duplicate-number/solution/er-fen-fa-si-lu-ji-dai-ma-python-by-liweiwei1419/。
LeetCode 第 300 题:最长上升子序列
题解地址:https://leetcode-cn.com/problems/longest-increasing-subsequence/solution/dong-tai-gui-hua-er-fen-cha-zhao-tan-xin-suan-fa-p/。
LeetCode 第 315 题:计算右侧小于当前元素的个数
LeetCode 第 421 题:数组中两个数的最大异或值
题解地址:https://leetcode-cn.com/problems/maximum-xor-of-two-numbers-in-an-array/solution/li-yong-yi-huo-yun-suan-de-xing-zhi-tan-xin-suan-f/。
LeetCode 第 1079 题:活字印刷
题解地址:https://leetcode-cn.com/problems/letter-tile-possibilities/solution/hui-su-suan-fa-python-dai-ma-by-liweiwei1419/。
LeetCode 第 1080 题:根到叶路径上的不足节点
题解地址:https://leetcode-cn.com/problems/insufficient-nodes-in-root-to-leaf-paths/solution/hou-xu-bian-li-python-dai-ma-java-dai-ma-by-liweiw/。
LeetCode 第 1081 题:不同字符的最小子序列
题解地址:https://leetcode-cn.com/problems/smallest-subsequence-of-distinct-characters/solution/tan-xin-suan-fa-zhan-wei-yan-ma-python-dai-ma-java/。
刷题过程中形成的文章
第 1 章 数组 | 代码文件夹 |
---|---|
LeetCode 数组专题 1:二分查找 | 链接地址 |
LeetCode 数组专题 2:一些关于数组的问题 | 链接地址 |
LeetCode 数组专题 3:三路快排 partition 的应用 | 链接地址 |
LeetCode 数组专题 4:双索引技术之一:对撞指针 | 链接地址 |
LeetCode 数组专题 5:双索引技术之二:滑动窗口 | 链接地址 |
LeetCode 数组专题 6:其它数组问题 | 链接地址 |
第 2 章 查找表 | 代码文件夹 |
LeetCode 查找表专题 1:查找问题简介 | 链接地址 |
LeetCode 查找表专题 2:哈希表的使用 | 链接地址 |
LeetCode 查找表专题 3:set 和 map 不同底层实现的区别 | 链接地址 |
LeetCode 查找表专题 4:使用查找表的经典问题:Two Sum | 链接地址 |
LeetCode 查找表专题 5:灵活选择键值:4Sum II | 链接地址 |
LeetCode 查找表专题 6:灵活选择键值:Number of Boomerangs | 链接地址 |
LeetCode 查找表专题 7:查找表和滑动窗口 | 链接地址 |
LeetCode 查找表专题 8:使用树结构 | 链接地址 |
第 3 章 单链表 | 代码文件夹 |
LeetCode 链表专题 1:在链表中穿针引线 | 链接地址 |
LeetCode 链表专题 2:测试你的链表程序 | 链接地址 |
LeetCode 链表专题 3:设立链表的虚拟头结点 | 链接地址 |
LeetCode 链表专题 4:复杂的穿针引线 | 链接地址 |
LeetCode 链表专题 5:不仅仅是穿针引线 | 链接地址 |
LeetCode 链表专题 6:链表与双指针 | 链接地址 |
第 4 章 栈、队列、优先队列 | 代码文件夹 |
LeetCode 栈、队列、优先队列专题 1:栈和队列的使用 | 链接地址 |
LeetCode 栈、队列、优先队列专题 2:二叉树的三种非递归实现 | 链接地址 |
LeetCode 栈、队列、优先队列专题 3:使用自己编写的模拟系统栈,写出非递归的程序 | 链接地址 |
LeetCode 栈、队列、优先队列专题 4:队列 Queue 与广度优先遍历 | 链接地址 |
LeetCode 栈、队列、优先队列专题 5:广度优先遍历和图的最短路径问题 | 链接地址 |
LeetCode 栈、队列、优先队列专题 6:优先队列也是队列 | 链接地址 |
第 5 章 二叉树和递归 | 代码文件夹 |
LeetCode 二叉树和递归专题 1:从二叉树的角度看递归 | 链接地址 |
LeetCode 二叉树和递归专题 2:一个简单的二叉树引发的血案 | 链接地址 |
LeetCode 二叉树和递归专题 3:注意递归的终止条件 | 链接地址 |
LeetCode 二叉树和递归专题 4:如何使用递归函数的返回值 | 链接地址 |
LeetCode 二叉树和递归专题 5:稍复杂的递归逻辑 Path Sum III | 链接地址 |
LeetCode 二叉树和递归专题 6:二分搜索树中的问题 | 链接地址 |
第 6 章 回溯问题 | 代码文件夹 |
LeetCode 回溯专题 1:在树形问题中使用递归 | 链接地址 |
LeetCode 回溯专题 2:回溯法是暴力解法的一个主要的实现手段 | 链接地址 |
LeetCode 回溯专题 3:排列问题 Permutations | 链接地址 |
LeetCode 回溯专题 4:组合问题 Combinations | 链接地址 |
LeetCode 回溯专题 5:回溯法解决组合问题的优化 | 链接地址 |
LeetCode 回溯专题 6:二维平面上使用回溯法 | 链接地址 |
LeetCode 回溯专题 7:floodfill 解决一类经典问题 | 链接地址 |
LeetCode 回溯专题 8:回溯法是经典的人工智能的基础 | 链接地址 |
第 7 章 动态规划问题 | 代码文件夹 |
LeetCode 动态规划专题 1:“重叠子问题”和“记忆化搜索” | 链接地址 |
LeetCode 动态规划专题 2:第 1 个动态规划问题的 3 种实现 | 链接地址 |
LeetCode 动态规划专题 3:第 2 个动态规划问题:整数分割 | 链接地址 |
LeetCode 动态规划专题 4:状态和状态转移方程 | 链接地址 |
LeetCode 动态规划专题 5:0-1 背包问题 | 链接地址 |
LeetCode 动态规划专题 6:0-1 背包问题在空间复杂度上的两个优化 | 链接地址 |
LeetCode 动态规划专题 7:面试中的 0-1 背包问题 | 链接地址 |
LeetCode 动态规划专题 8:最长上升子序列问题 | 链接地址 |
第 8 章 贪心算法 | 代码文件夹 |
LeetCode 专题:贪心算法 | 链接地址 |
第 9 章 拓扑排序 | 代码文件夹 |
LeetCode 专题:拓扑排序 | 链接地址 |
第 10 章 字典树 | 代码文件夹 |
【算法日积月累】20-高级数据结构:字典树 | 链接地址 |
第 11 章 并查集 | 代码文件夹 |
【算法日积月累】17-高级数据结构:并查集 | 链接地址 |
第 12 章 位运算 | 代码文件夹 |
LeetCode 专题:位运算 | 链接地址 |
第 13 章 树状数组 | 代码文件夹 |
【算法日积月累】19-高级数据结构:树状数组 | 链接地址 |
第 14 章 分治算法 | 代码文件夹 |
[整理中] | |
第 15 章 二分查找 | 代码文件夹 |
LeetCode 专题:二分查找 | 链接地址 |
第 16 章 线段树 | 代码文件夹 |
【算法日积月累】18-高级数据结构:线段树 | 链接地址 |
第 17 章 数学问题 | 代码文件夹 |
[整理中] | |
第 18 章 优先队列 | 代码文件夹 |
[整理中] | |
第 19 章 字符串 | 代码文件夹 |
[整理中] |