【算法集训 | 暑期刷题营】8.11题---回溯与剪枝

简介: 【算法集训 | 暑期刷题营】8.11题---回溯与剪枝

 👉引言


铭记于心
🎉✨🎉我唯一知道的,便是我一无所知🎉✨🎉


💖 ❄️我们的算法之路❄️💖


   众所周知,作为一名合格的程序员,算法 能力 是不可获缺的,并且在算法学习的过程中我们总是能感受到算法的✨魅力✨。

☀️🌟短短几行代码,凝聚无数前人智慧;一个普通循环,即是解题之眼🌟☀️

💝二分,💝贪心,💝并查集,💝二叉树,💝图论,💝深度优先搜索(dfs) ,💝宽度优先搜索(bfs) ,💝数论,💝动态规划等等, 路漫漫其修远兮,吾将上下而求索! 希望在此集训中与大家共同进步,有所收获!!!🎉🎉🎉

image.png


今日主题:回溯与剪枝


 👉⭐️第一题💎


   ✨题目


     40. 组合总和 II

image.png


   ✨思路:


主要利用回溯与剪枝,对于这种不重复选取问题,关键就是找到一个顺序,所以先排序,让每一次选取都大于等于之前,然后利用hash或者candidates[i]>candidates[begin]进行剪枝


   ✨代码:


class Solution {
public:
 void dfs(vector<vector<int>> &ans, vector<int> &tem, vector<int> &candidates, int target, set<int> &f, int sum)
{
    if (sum == target)
    {
        ans.emplace_back(tem);
        return;
    }
    int n = candidates.size();
    set<int> isHas;
    for (int i = 0; i < n; i++)
    {
        if (f.find(i) != f.end())
            continue;
        if (isHas.find(candidates[i]) != isHas.end())
            continue;//这里可以不使用哈希,直接设定同级选取必须比之前大,也就是可以将条件改为 candidates[i]>candidates[begin],上面让i从begin开始
        if (!tem.size() || candidates[i] >= tem.back())
        {
            int S = sum + candidates[i];
            if (target >= S)
            {
                tem.emplace_back(candidates[i]);
                isHas.insert(candidates[i]);
                f.insert(i);
                dfs(ans, tem, candidates, target, f, S);
                f.erase(i);
                tem.pop_back();
            }
            else
                break;
        }
    }
}
vector<vector<int>> combinationSum2(vector<int> &candidates, int target)
{
    vector<vector<int>> ans;
    vector<int> tem;
    int sum = 0;
    set<int> f;
    sort(candidates.begin(),candidates.end());
    dfs(ans, tem, candidates, target, f, sum);
    return ans;
}
};

image.png


 👉⭐️第二题💎


   ✨题目


     46. 全排列


image.png


   ✨思路:


经典的DFS回溯问题,可以直接套用模板 ,首先对第一个位置用一个for循环遍历数组,然后做标记,然后递归选取后面的位置,同级for循环时如果是引用传递,则需要注意回溯(恢复现场),而由于C++直接提供了全排列函数,这里就直接用上


   ✨代码:


class Solution {
public:
    vector<vector<int>> permute(vector<int>& nums) {
        sort(nums.begin(),nums.end());
        vector<vector<int>> res;
        do{
            res.emplace_back(nums);
        } while (next_permutation(nums.begin(), nums.end()));
        return res;
    }
};


 👉⭐️第三题💎


   ✨题目


      473. 火柴拼正方形

image.png


   ✨思路:


维护一个大小为4的数组,表示正方形每条边的位置,然后尝试对于每个火柴这4个位置都放一遍(纯暴力搜索),时间复杂度 O( 4 n 4^{n} 4n) ,一定 TLE,所以进行剪枝 1.将数组从大到小排序,减少搜索次数 2. 只有当该位置的数小于等于avg时,才能将火柴放置 3.数组总和必定要是4的倍数 还有种写法是状态压缩+dp,这里就不详细介绍了,有兴趣的请移步官方题解


   ✨代码:


class Solution
{
public:
    vector<int> edge;
    int avg;
    bool dfs(int index, vector<int> &matchsticks)
    {
        if (index == matchsticks.size())        return true;
        for (int i = 0; i < 4; i++)
        {
            edge[i] += matchsticks[index];
            if (edge[i] > avg)
            {
                edge[i] -= matchsticks[index];
                continue;
            }
            if (dfs(index + 1, matchsticks))  return true;
            edge[i] -= matchsticks[index];
        }
        return false;
    }
    bool makesquare(vector<int> &matchsticks)
    {
        sort(matchsticks.begin(),matchsticks.end(),greater<int>());
        for (int i : matchsticks)
            avg += i;
        if(avg%4)return false;
        avg/=4;
        edge.resize(4);
        return dfs(0, matchsticks);
    }
};


 👉⭐️第四题💎


   ✨题目


      A. Red Versus Blue


image.pngimage.png


   ✨代码:


#include<bits/stdc++.h>
using namespace std;
using lol=long long int;
#define endl "\n"
int main()
{
ios_base::sync_with_stdio(false);
cin.tie(NULL);
int _=1;
cin>>_;
while(_--)
{
    int n,r,b;
    cin>>n>>r>>b;
    int p=r/(b+1),q=r%(b+1);
    for(int i=0;i<q;i++)    cout<<string(p+1,'R')<<'B';
    for(int i=q;i<b;i++)    cout<<string(p,'R')<<'B';
    cout<<string(p,'R');
    cout<<endl;
}
return 0;
}

写在最后

相信大家对今天的集训内加粗样式容的理解与以往已经有很大不同了吧,或许也感受到了算法的魅力,当然这是一定的,路漫漫其修远兮,吾将上下而求索!伙伴们,明天见!


相关文章
|
1月前
|
存储 算法 安全
2024重生之回溯数据结构与算法系列学习之串(12)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丟脸好嘛?】
数据结构与算法系列学习之串的定义和基本操作、串的储存结构、基本操作的实现、朴素模式匹配算法、KMP算法等代码举例及图解说明;【含常见的报错问题及其对应的解决方法】你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
2024重生之回溯数据结构与算法系列学习之串(12)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丟脸好嘛?】
|
1月前
|
算法 安全 搜索推荐
2024重生之回溯数据结构与算法系列学习(8)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构王道第2.3章之IKUN和I原达人之数据结构与算法系列学习x单双链表精题详解、数据结构、C++、排序算法、java、动态规划你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
|
1月前
|
存储 算法 安全
2024重生之回溯数据结构与算法系列学习之顺序表【无论是王道考研人还真爱粉都能包会的;不然别给我家鸽鸽丢脸好嘛?】
顺序表的定义和基本操作之插入;删除;按值查找;按位查找等具体详解步骤以及举例说明
|
1月前
|
算法 安全 搜索推荐
2024重生之回溯数据结构与算法系列学习之单双链表精题详解(9)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构王道第2.3章之IKUN和I原达人之数据结构与算法系列学习x单双链表精题详解、数据结构、C++、排序算法、java、动态规划你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
|
1月前
|
存储 Web App开发 算法
2024重生之回溯数据结构与算法系列学习之单双链表【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构之单双链表按位、值查找;[前后]插入;删除指定节点;求表长、静态链表等代码及具体思路详解步骤;举例说明、注意点及常见报错问题所对应的解决方法
|
1月前
|
算法 安全 NoSQL
2024重生之回溯数据结构与算法系列学习之栈和队列精题汇总(10)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构王道第3章之IKUN和I原达人之数据结构与算法系列学习栈与队列精题详解、数据结构、C++、排序算法、java、动态规划你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
|
1月前
|
算法 安全 NoSQL
2024重生之回溯数据结构与算法系列学习之顺序表习题精讲【无论是王道考研人还真爱粉都能包会的;不然别给我家鸽鸽丢脸好嘛?】
顺序表的定义和基本操作之插入;删除;按值查找;按位查找习题精讲等具体详解步骤以及举例说明
|
1月前
|
存储 算法 安全
2024重生之回溯数据结构与算法系列学习【无论是王道考研人还真爱粉都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构的基本概念;算法的基本概念、特性以及时间复杂度、空间复杂度等举例说明;【含常见的报错问题及其对应的解决方法】
|
1月前
|
算法 安全 搜索推荐
2024重生之回溯数据结构与算法系列学习之王道第2.3章节之线性表精题汇总二(5)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
IKU达人之数据结构与算法系列学习×单双链表精题详解、数据结构、C++、排序算法、java 、动态规划 你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
|
1月前
|
算法
”回溯算法“框架及练习题
”回溯算法“框架及练习题
44 0