Introduction
If the full score is 100, no matter your background, this site can help you reach a score of 85 in the shortest time.
This is because the site teaches you to use templates and frameworks. You can always get to this 85 by following the methods here. For problems below 85 in difficulty, you can solve them step by step. Only for problems harder than 85, you need luck and inspiration.
What does 85 mean?
For example, if you studied computer science in college, took data structure and algorithm courses, mainly used development frameworks at work, and never practiced algorithm problems, your score is probably around 30-40. This is true. Algorithm skills are independent, not directly related to programming experience. You need special practice to improve.
So, don't think 85 is low. This is already enough for most tech interviews and basic contests. Don't fear algorithms. If you use the right methods and spend time practicing, it's easy to improve.
Site Structure
Introduction
Tools and Algorithm Visualization
Algorithm Visualization Introduction Algorithm Game Introduction Chrome Extension for LeetCode vscode Plugin for LeetCode JetBrains Plugin for LeetCode Subscribe to this Algo Notes
Study Plans for Beginners and Quick Mastery
Learning Plan for Beginners Learning Plan for Quick Mastery How to Learn Algorithms Efficiently How to Practice
Programming Language Basics
Chapter Introduction C++ Basics Java Basics Golang Basics Python Basics JavaScript Basics LeetCode Guide Let's Have Fun with LeetCode
Getting Started: Data Structures and Sorting
Implement Dynamic Arrays
Implement Single/Double Linked List
Array and LinkedList Variations
Implement Queue and Stack
Implement HashMap
Hash Table Variations
Binary Tree Structure and Traversal
Binary Tree Variations
Graph Structure and Algorithm Overview
Implement and Visualize 10 Sorting Algorithms
Chapter Introduction Key Metrics of Sorting Algorithms Explore Selection Sort in Depth Bubble Sort with Stability Insertion Sort with Reverse Thinking Shell Sort - Better than O(N^2) Quick Sort and Binary Tree Preorder Merge Sort and Binary Tree Postorder Heap Sort and Binary Heap Counting Sort: A New Pespective on Sorting Bucket Sort Radix Sort
Updating
Chapter 0. Classic Problem Solving Templates
Chapter Introduction How to Think About Data Structure and Algorithm Two Pointer Techniques for Linked List Problems Two Pointer Techniques for Array Problems Sliding Window Algorithm Code Template Thinking Recursion Algorithms from Binary Tree Perspective One Perspective + Two Thinking Patterns to Master Recursion Dynamic Programming Common Patterns and Code Template Backtracking Algorithm Common Patterns and Code Template BFS Algorithm Common Patterns and Code Template Backtracking Algorithm to Solve All Permutation/Combination/Subset Problems Greedy Algorithms Principles and Techniques Divide and Conquer Principles and Techniques Time and Space Complexity Analysis Practical Guide
Chapter 1. Data Structure Algorithms
Linked List Algorithm
Array Algorithm
Two Pointer Techniques for Array Problems Tricks to Traverse a 2D Array Exercise: Two Pointer Techniques for Array One Trick to Solve All N-Sum Problems Prefix Sum Array Technique Exercise: Prefix Sum Techniques Difference Array Technique Sliding Window Algorithm Code Template Exercise: Sliding Window In Action Sliding Window Application: Rabin Karp String Matching Algorithm Binary Search Algorithm Code Template Binary Search in Action Exercise: Binary Search Algorithm Weighted Random Selection Algorithm Advantage Shuffle Algorithm
Stack/Queue Algorithm
Implement Stack with Queue, Implement Queue with Stack Exercise: Stack Problems on LeetCode Exercise: Bracket Problems on LeetCode Exercise: Queue Problems on LeetCode Monotonic Stack Code Template Exercise: Monotonic Stack Problems on LeetCode Monotonic Queue to Solve Sliding Window Problems Exercise: Monotonic Queue Implementation and Leetcode Problems
Binary Tree Algorithm
Thinking Recursion Algorithms from Binary Tree Perspective Binary Tree in Action (Traversal) Binary Tree in Action (Construction) Binary Tree in Action (Post-order) Binary Tree in Action (Serialization) Binary Search Tree in Action (In-order) Binary Search Tree in Action (Basic Operations) Binary Search Tree in Action (Construction) Binary Search Tree in Action (Post-order)
Master Binary Tree Problems
Chapter Introduction Exercise: Binary Tree Traversal I Exercise: Binary Tree Traversal II Exercise: Binary Tree Traversal III Exercise: Binary Tree Divide and Conquer I Exercise: Binary Tree Divide and Conquer II Exercise: Binary Tree Combine Two Views Exercise: Binary Tree Post-order I Exercise: Binary Tree Post-order II Exercise: Binary Tree Post-order III Exercise: Binary Tree Level I Exercise: Binary Tree Level II Exercise: Binary Search Tree I Exercise: Binary Search Tree II
Binary Tree Follow-up
Design Data Structures
Implementing LRU Cache like Building a Lego Implementing LFU Cache like Building a Lego How to Deleting Array Element in O(1) Time Exercise: Hash Table Problems on LeetCode Exercise: Priority Queue Problems on LeetCode Implementing TreeMap/TreeSet Basic Segment Tree Implementation Dynamic Segment Tree Implementation Lazy Update Segment Tree Implementation Exercise: Segment Tree Problems Implementing Trie Tree Exercise: Trie Problems on LeetCode Designing a Twitter Feed Designing an Exam Room Algorithm Exercise: Classic Design Problems on LeetCode How to Implement a Calculator Implementing Median Algorithm with Two Binary Heaps Removing Duplicates from an Array (Hard Version)
Graph Algorithm
How to Determine a Bipartite Graph Hierholzer Algorithm to Find Eulerian Path Exercise: Eulerian Path Cycle Detection and Topological Sort Algorithm Union-Find Algorithm Exercise: Union-Find Problems on LeetCode Dijkstra Principles and Implementation Dijkstra Algorithm with Restrictions Exercise: Dijkstra Problems Kruskal Minimum Spanning Tree Algorithm Prim Minimum Spanning Tree Algorithm
Chapter 2. Brute Force Search
DFS and Backtracking Algorithm
Backtracking Algorithm Common Patterns and Code Template Backtracking in Action: Sudoku and N-Queens Implement Sudoku Cheat Backtracking Algorithm to Solve All Permutation/Combination/Subset Problems Some Questions About Backtracking and DFS Algorithms Solve All Island Problems with DFS Minesweeper Game II Ball and Box: Two Perspectives of Backtracking Enumeration Backtracking Algorithm Practice: Generating Valid Parentheses Backtracking Algorithm Practice: Partitioning k Subsets Exercise: Backtracking Problems on LeetCode I Exercise: Backtracking Problems on LeetCode II Exercise: Backtracking Problems on LeetCode III
BFS Algorithm
Chapter 3. Dynamic Programming Algorithms
Basic DP Techniques
Dynamic Programming Common Patterns and Code Template How to Design Transition Equations How to Determine the Base Case and Initial Values for Memoization? Two Perspectives of Dynamic Programming Enumeration How to Convert Backtracking to Dynamic Programming Optimize Space Complexity for Dynamic Programming Clarifying Some Questions About Dynamic Programming
Subsequence Problems
Knapsack Problems
Dynamic Programming Game
Classic DP: Minimum Path Sum Play Dungeon Game with DP Play Freedom Trail with DP Save Money on Your Trip: Weighted Shortest Path Classic DP: Regular Expression Matching Classic DP: Egg Drop Classic DP: Burst Balloons Classic DP: Game Theory One Method to Solve All House Robber Problems on LeetCode One Method to Solve all Stock Problems on LeetCode
Dynamic Programming ProblemSet
Greedy
Chapter 4. Other Common Techniques
Mathematical Techniques
LeetCode Problems with One Line Solution Common Bit Manipulation Techniques Minesweeper Game I Random Algorithms in Games Two Classic Factorial Problems on LeetCode How to Efficiently Count Prime Numbers How to Efficiently Perform Modular Exponentiation How to Find Missing and Duplicate Elements Interesting Probability Problems Exercises: Math Tricks
Classic Interview Problems
Tips for Algorithmic Exams How to Efficiently Solve the Trapping Rain Water Problem One Article to Solve All Ugly Number Problems on LeetCode One Method to Solve Three Interval Problems on LeetCode Split Array into Consecutive Subsequences Pancake Sorting Algorithm String Multiplication Calculation How to Determine if a Rectangle is Perfect
Appendix
How to Read
If you have little time and need to quickly prepare (less than 30 days), follow the Quick Mastery Plan.
If you already have some experience (solved more than 300 problems), you must read Chapter 0. You can choose other chapters as needed.
If you are a beginner, read in order, step by step, following the site structure.
This site works well on both PC and mobile. You can prepare for algorithm interviews and written tests all in one place.

About the Content
The content includes both written tutorials and videos, mainly divided into three parts:
1️⃣ Data Structure Tutorials (about 10% of the site)
Focused in Data Structures and Sorting. These teach sorting and key data structures, with explanations and code. This part does not have algorithm problems. It helps you understand common data structures for work and special ones used in algorithm problems, so you can use them when solving problems later.
2️⃣ Classic Algorithm Frameworks Explained with Examples (about 50% of the site)
For classic algorithm frameworks or problems, I write whole articles to explain with real examples. The goal is to help you understand the idea. Each article usually has 2-5 example problems. You can solve them as you read.
3️⃣ Exercise Chapters to Practice Frameworks (about 40% of the site)
Chapters marked Practice
are for practice. They come right after the framework explanations. All practice problems can use the taught frameworks directly. The goal is to help you build muscle memory by repeating. Each exercise has 5-10 problems. Once you understand the framework, you can solve them quickly.
This site helps you solve hundreds of free LeetCode problems. Most are for practicing the frameworks. Once you get the method, you can solve them in minutes.
LeetCode Problem List
Some readers asked for a list of all problems covered on this site. After installing the Chrome extension, you can open the list to see all problems with solution notes from this site.
But, I think this list is not very useful and I do not suggest practicing by this list. The order is random, you can't learn step by step, and can't focus on a certain topic. You also don't need to finish all these problems. Once you master the frameworks, most problems become easy and do not need extra practice.
LeetCode China | LeetCode Global |
---|---|
https://leetcode.cn/problem-list/59jEaTgw/ | https://leetcode.com/list/9zwo3ww5/ |
I suggest following the Beginner Plan or the Quick Mastery Plan, which have organized lists by topic. The VSCode extension and Jetbrains extension also include these plans for easy access.

Expired URLs, PDFs, and Content
The latest and only official site is always: labuladong.online.
I keep updating and improving the tutorials here. Some old sites and content are now outdated and should not be used, because better and clearer materials are now available.
Tutorials I posted on other platforms are outdated and no longer updated.
The following old URLs are no longer maintained:
Old PDFs are also outdated, including "labuladong's Algorithm Cheat Sheet", "labuladong's Practice Notes", and "labuladong's Algorithm Secrets".
I care a lot about your learning experience and keep updating and improving the content. At the top, you can find update logs and bug feedback.
About the Author
I am labuladong, author of the fucking-algorithm repo. Readers usually call me "Dong Ge". I created the framework thinking method for solving problems. My repo often tops GitHub Trending and has over 125k stars.
I focus on making things simple and to the point. This site is only for algorithm practice, helping you master algorithms quickly and efficiently.
Site subscription is the only paid feature. For the price of a meal, you can unlock all tutorials and tools on this site and enjoy a smooth learning experience.
Useful Features of This Site
1. Algorithm Visualization
On this site and in all related plugins, there is an algorithm visualization panel below each solution code. You can see how the algorithm works step by step. This helps you understand the logic of the algorithm.
For example, in the Find the Start of the Cycle in a Linked List algorithm, you can click the code if (fast == slow) break
several times to see how the fast and slow pointers meet. Click the code while (slow != fast)
several times to see how the pointers move together and meet at the start of the cycle.
Example 1: Color System and Interaction
The visualization panel also supports complex data structures and recursive algorithms. Here is a DFS traversal on a graph to find all paths from node 0
to node 4
. Click the code if (s === n - 1)
several times to watch the graph traversal and how the recursion tree grows.
Example 2: Complex Structures and Recursion
The visualization panel can show data structures in different ways to help you understand.
For example, below is an array shown as a bar chart. It shows the steps of Insertion Sort. You can click the play button in the top left to speed up and watch the sorting process.
Example 3: Sorting Algorithm
The visualization panel makes it much easier to understand complex algorithms. It supports all data structures and algorithms. Here are just a few examples. For more classic algorithm visualizations, see the Algorithm Visualization Quick Reference.
2. Learn and Apply Algorithms with Game Engines
The visualization panel helps you see how algorithms work. But just solving problems is not enough. I want to help you use algorithms in real life, and show the fun side of algorithms, so you will truly enjoy learning them.
One of my ideas is to combine algorithms and games. Usually, we play games with our hands, but can we use algorithms to play games instead?
So, I have designed some classic small games. I separate the algorithm parts and give you a game scene. You can write algorithms to control the game engine. In the end, you get a running game or complete a game task (which would be hard to do by hand).
This way, you can get a strong sense of achievement. More importantly, you can see how algorithms are used in real scenarios and understand them better.
For example, here is a Snake game. You can write code for the snake's movement and how it eats food. The game will run using your code. It may seem hard at first, but it is simple if you use basic linked list operations:
For more fun games, see Algorithm Games and Summary.
3. Supports All Popular Programming Languages
All solution codes on this site and in all plugins support all common programming languages, including Java, C++, Python, Golang, JavaScript, and more. This is to help as many readers as possible.
All code has been tested and checked by me to make sure it is correct and consistent.
The site and plugins also support code image notes. For complex code, there is a small lightbulb icon. Move your mouse over the lightbulb to see helpful images.
class Solution {
public ListNode detectCycle(ListNode head) {
ListNode fast, slow;
fast = slow = head;
while (fast != null && fast.next != null) {
fast = fast.next.next;
slow = slow.next;
if (fast == slow) break;
}
// the above code is similar to the hasCycle function
if (fast == null || fast.next == null) {
// fast encountering a null pointer means there is no cycle
return null;
}
// reassign to the head node
slow = head;
// move fast and slow pointers at the same pace, the
// intersection point is the cycle's entry point
while (slow != fast) {
fast = fast.next;
slow = slow.next;
}
return slow;
}
}
class Solution {
public:
ListNode *detectCycle(ListNode *head) {
ListNode *fast, *slow;
fast = slow = head;
while (fast != nullptr && fast->next != nullptr) {
fast = fast->next->next;
slow = slow->next;
if (fast == slow) break;
}
// the above code is similar to the hasCycle function
if (fast == nullptr || fast->next == nullptr) {
// if fast encounters a null pointer, it means there is no cycle
return nullptr;
}
// reset to the head node
slow = head;
// move the fast and slow pointers forward in sync, the
// intersection point is the start of the cycle
while (slow != fast) {
fast = fast->next;
slow = slow->next;
}
return slow;
}
};
class Solution:
def detectCycle(self, head: ListNode):
fast, slow = head, head
while fast and fast.next:
fast = fast.next.next
slow = slow.next
if fast == slow:
break
# the above code is similar to the hasCycle function
if not fast or not fast.next:
# if fast encounters a null pointer, it means there is no cycle
return None
# reset the pointer to the head node
slow = head
# both fast and slow pointers move forward in sync, the
# intersection point is the start of the cycle
while slow != fast:
fast = fast.next
slow = slow.next
return slow
func detectCycle(head *ListNode) *ListNode {
fast, slow := head, head
for fast != nil && fast.Next != nil {
fast = fast.Next.Next
slow = slow.Next
if fast == slow {
break
}
}
// the above code is similar to the hasCycle function
if fast == nil || fast.Next == nil {
// if fast encounters a null pointer, it means there is no cycle
return nil
}
// reset the pointer to the head node
slow = head
// move the fast and slow pointers forward in sync,
// the intersection point is the start of the cycle
for slow != fast {
fast = fast.Next
slow = slow.Next
}
return slow
}
var detectCycle = function(head) {
let fast, slow;
fast = slow = head;
while (fast !== null && fast.next !== null) {
fast = fast.next.next;
slow = slow.next;
if (fast == slow) break;
}
// the above code is similar to the hasCycle function
if (fast === null || fast.next === null) {
// if fast encounters a null pointer, it means there is no cycle
return null;
}
// reset the pointer to the head node
slow = head;
// move the fast and slow pointers forward in sync,
// the intersection point is the start of the cycle
while (slow !== fast) {
fast = fast.next;
slow = slow.next;
}
return slow;
};
4. Other Useful Features
Reading history is supported. In the sidebar and inside articles, links to unread articles show a
Focus mode is supported. When you visit the site on a computer, there is a "Focus Mode" switch at the top right. Turn it on to blur the sidebar and top bar. This helps you focus or learn at work.
Site-wide search is supported. The search box at the top right lets you search the whole site. You can also enter a LeetCode problem, number, or link to find the explanation directly.
5. Helpful Plugins for Practicing Problems
To meet different needs, I have developed plugins for this site. You can use them to practice coding in your favorite editor, and slack off at work.
The plugins include the Beginner Directory and Quick Mastery Directory. You can debug code locally, and easily see explanations, visual panels, image notes, and more.
The plugins are not required, but I suggest installing the Chrome browser plugin. When you read this site, you may often jump to LeetCode to practice. The Chrome plugin can help you. The vscode/Jetbrain plugins can be installed if you want to practice in those editors.
See Chrome Plugin, vscode Plugin, and Jetbrain Plugin for how to install and use each plugin.