leetcode分类刷题(续2)

本文汇总了LeetCode中的递归、分治、回溯法和动态规划技巧,涉及斐波那契数列、链表反转、字符串翻转、归并排序、多数元素、最大子序和、k大元素、子集生成、括号组合、全排列等经典题目。深入解析算法原理,并提供实例代码。

1. 递归

函数直接或者间接调用自己
四个要素:接受的参数,返回值,终止条件,递归拆解

1.1 leetcode509 斐波拉契数列

1.2 leetcode206 反转链表

//伪代码
function(head){
	if(head == null or head.next == null )
		return head;
	
	p =  function(head.next);
	head.next.next = head;
	head.next =  null;

	return p;
}

1.3 leetcode344 反转字符串

 双指针互换                        

2. 分治法

概念:大问题切割成一个个小问题,再合并

2.1 归并排序


2.2 leetcode169 多数元素


2.3 leetcode53 最大子序和

连续子数组
子数组

2.4 leetcode215 数组中k大元素


3. 回溯法

概念:类似枚举,一层一层向下递归,尝试搜索答案
找到答案: 返回答案或者尝试别的可能
找不到答案:返回上一层递归,尝试别的路径
组合问题:
回溯算法:求组合问题!
回溯算法:组合问题再剪剪枝
回溯算法:求组合总和!
回溯算法:电话号码的字母组合
回溯算法:求组合总和(二)
回溯算法:求组合总和(三)

分割问题:
回溯算法:分割回文串
回溯算法:复原IP地址

3.1 leetcode78 子集(模板)

找到所有子集
1. 扩展法 一个一个数扩展
2. 回溯法
3. DFS
  1. 回溯法
class Solution {
    public List<List<Integer>> subsets(int[] nums) {
        List<Integer> list = new ArrayList<Integer>();
        List<List<Integer>> ans = new LinkedList<List<Integer>>();
         ans.add(new ArrayList<>());
        if(nums.length == 0){
            return ans;
        }

        for(int i = 1; i<=nums.length; i++){
            backtracking(nums,ans,i,0,new ArrayList<>());    
        }
        return ans;
    }
    private void backtracking(int[] nums,List<List<Integer>> ans,int length,int index,List<Integer> subset){
        if(subset.size() == length){
            List<Integer> temp = new ArrayList<>(subset);
            ans.add(temp);
            return; 
        }

        for(int i = index;i<nums.length;i++){
            subset.add(nums[i]);
            backtracking(nums,ans,length,i+1,subset);
            subset.remove(subset.size()-1);
        }
    }
}

3.2 leetcode22 括号生成

3.3 leetcode77 组合

3.4 leetcode46 全排列

3.5 leetcode17 电话号码的字母组合

4. DFS

4.1 leetcode78 子集

//深度遍历---也是一种递归,一条路走到底。

4.2 leetcode938 二叉搜索树的范围和

//递归方式:
class Solution {
    public int rangeSumBST(TreeNode root, int low, int high) {
        if(root ==null)
            return 0;
            
        int leftsum = rangeSumBST(root.left,low,high);
        int rightsum = rangeSumBST(root.right,low,high);

        int result = leftsum + rightsum;
        if((root.val<=high)&&(root.val>=low)){
            result = result + root.val;
        }   
        return result;
    }
}

4.3 leetcode200 岛屿数量

动态规划:

5. BFS

层次遍历: 队列

5.1 leetcode102 二叉树的层序遍历

5.2 leetcode107 二叉树的层序遍历Ⅱ

class Solution {
    public List<List<Integer>> levelOrderBottom(TreeNode root) {
        List<List<Integer>> levelOrder = new LinkedList<List<Integer>>();
        if (root == null) {
            return levelOrder;
        }
        Queue<TreeNode> queue = new LinkedList<TreeNode>();
        queue.offer(root);
        while (!queue.isEmpty()) {
            List<Integer> level = new ArrayList<Integer>();
            int size = queue.size();
            for (int i = 0; i < size; i++) {
                TreeNode node = queue.poll();
                level.add(node.val);
                TreeNode left = node.left, right = node.right;
                if (left != null) {
                    queue.offer(left);
                }
                if (right != null) {
                    queue.offer(right);
                }
            }
            levelOrder.add(0,level);
        }
        return levelOrder;
    }
}

5.3 leetcode200 岛屿数量

// An highlighted block
var foo = 'bar';

6. 并查集 Union Find

// An highlighted block
var foo = 'bar';

6.1 leetcode200 岛屿数量

// An highlighted block
var foo = 'bar';

6.2 leetcode547 朋友圈

// An highlighted block
var foo = 'bar';

7. 贪心算法

局部最优解
var foo = 'bar';

7.1 leetcode322 零钱兑换

最少的硬币

7.2 leetcode1217 玩筹码


7.3 leetcode55 跳跃游戏


8. 动态规划 Dynamic Programming

题型千遍万化 思路千遍万化
经典题型:左上角到右下角 多少路径?
同门已经刷到160题了 加油
斐波拉契数列-----动态规划思想:
初始状态+方程式+终止状态
填一个一维或者二维表,初始状态---> 状态转移方程式 ---> 终止状态

重点:
 1. 计数: 有多少种方式,方法 (机器人从左上角到右下角多少个路径)
 2. 求最值: 最大值,最小值 (机器人从左上角到右下角得最大数字和)
 3. 求存在性:是否存在某个路径的可能(是否存在机器人从左到右的路径)

8.1 leetcode509 斐波那契数


8.2 leetcode62 不同路径


8.3 leetcode121 买卖股票的最佳时机


8.4 leetcode70 爬楼梯



8.5 leetcode279 完全平方数


8.6 leetcode221 最大正方形


8.7 leetcode198 打家劫舍

class Solution {
    public int rob(int[] nums) {
        if(nums.length == 1)
            return nums[0]; 
        if(nums.length == 2)
            return(Math.max(nums[0],nums[1]));
        int[] dp = new int[nums.length];
        dp[0] = nums[0];
        dp[1] = Math.max(nums[0],nums[1]);
        for(int i = 2; i< nums.length; i++){
            dp[i] = Math.max((nums[i]+dp[i-2]),dp[i-1]);
        }
        return dp[nums.length-1];
    }
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值