【递归、搜索与回溯】综合练习三

news2024/12/24 8:35:38

综合练习三

  • 1.优美的排列
  • 3.N 皇后
  • 3.有效的数独
  • 4.解数独

在这里插入图片描述

点赞👍👍收藏🌟🌟关注💖💖
你的支持是对我最大的鼓励,我们一起努力吧!😃😃

1.优美的排列

题目链接:526. 优美的排列

题目描述:

在这里插入图片描述

注意一个数字只要能满足 perm[i] 能够被 i 整除 或者 i 能够被 perm[i] 整除,就是优美排列中的数字。

在这里插入图片描述
算法原理:
画出决策树,把所有情况不重不漏的找出来。
我们一个位置一个位置的去找,每个位置都有三种选择,但是要注意上一个位置选过的数下一个位置就不要选了。因此可以来一个全局bool 类型数组,记录每个数是否被选过。还有满足 perm[i] 能够被 i 整除 或者 i 能够被 perm[i] 整除 的数才能选。因为这里不需要统计每个组合是什么,我们也不需要path。而只需统计满足情况的有几种就行了。

在这里插入图片描述

class Solution {
    int ret;
    bool check[16];
public:
    int countArrangement(int n) {

        dfs(n,1);
        return ret;
    }

    void dfs(int n,int pos)
    {
        if(pos == n+1)
        {
            ++ret;
            return;
        }

        for(int i=1;i<=n;++i)
        {
            if(check[i] == false && (i%pos == 0 || pos%i == 0))
            {
                check[i]=true;
                dfs(n,pos+1);
                check[i]=false; //恢复现场
            }
        }
    }
};

3.N 皇后

题目链接:51. N 皇后

题目分析:

在这里插入图片描述

给一个n,代表的是n*n的棋盘,在这个棋盘上放皇后。按照国际象棋的规则,皇后可以攻击与之处在同一行或同一列或同一斜线上的棋子。因此放皇后然后使皇后彼此之间不能相互攻击。问有几种解决方案?

算法原理:
这道题决策树还是比较好看画的,难的是如何剪枝+代码能力!
N皇后的决策树有两种画法,第一种比较麻烦,就是一个小格子一个小格子的来考虑能不能放。第二种就是考虑每次只考虑一行这个皇后应该放哪里。

每行都有n个位置可以放皇后,但是如果放皇后位置满足,皇后在一行或一列或者正对角线或者副对角线的,这个皇后就不能放!全局变量一个ret,一个path,回溯都和前面是一样的。递归函数,就是告诉我一个行数,我就尝试把每一个格子尝试放一个皇后,如果能放就放然后考虑下一行。dfs(row)。递归出口 row==n,说明遇到合法的情况,然后把path放到ret里。我们主要就说剪枝的情况。

在这里插入图片描述
接下来就是剪枝的情况了。
何剪枝:考虑当前这个位置,能否放上皇后?
有两种方法:
1.无脑循环。来四个循环,分别看同一行、同一列、主对角线、右对角线是否有皇后。有这个位置就不能放皇后,都没有就可以放皇后。
在这里插入图片描述
这里我们可以优化一下,没有必要四层循环,三层循环就够了。因为我们都一行一行的枚举,每一行要么第一列放,其他列不放。要么第二列放,其他列不放。要么第三列放,其他列不放。行决定不会出现相互攻击的情况,所有只用看看这一列,主对角线,副对角线有没有。

2.类似哈希表的策略
类似于五子棋那种常用的策略。仅用三个数组就可以搞定!
此时我判断某一列是否有皇后,可以搞一个bool类型大小为n的数组,bool col[n],就可以了。当在0列放一个皇后的时候,可以让col[0]=true, 说明这一列有皇后了。当到其他行的时候第一列就去看col[0]是否等于ture,等于true说明有皇后,不放就可以了。
在这里插入图片描述

接下来考虑主对角线和副对角线。我们把这几个位置抽象成几个点放到坐标系里。
主对角线不都是一条斜线吗,主对角线条数=2n-1, 这里是5条,我们就判断这5条对角线就可以了。我们这几条对角线的斜率都是1,因此所有线都可以用 y=x+b表示,此时移位就变成了 y-x=b,这个公式表达的意思是,就看这条红线,它上面的点用纵坐标减去横坐标是一个定值b ,因此继续**搞一个bool类型大小为2n的数组**,当我们发现y-x=b在数组里面是true的话,就说明这个对角线里面有皇后了。因为这个对角线里面y-x全都是一个定值。所以可以把这个定值放到数组下标里面,如果这个位置等于的true,表示这条对角线有皇后了,如果等于false,说明这条对角线没有皇后。
在这里插入图片描述
但是这里有一个问题,y-x这里是一个负数,在bool类数组下标里面是不存在负数的,没问题左右两边添加一个偏移量 y-x+n = b+n,通通向上平移n个单位。绝对是一个正数。因此我们求主对角线的时候,就是y-x+n去数组里面看看如果是true,有皇后。如果是false,没有皇后。
在这里插入图片描述
副对角线 斜率为-1, 那就是y=-x+b,此时移位 y+x=b,也就是这单单一条线里面,每一个点横坐标+纵坐标都是一个定值,所以我们又可以搞一个bool类型大小为2*n的数组。当我判断某个位置副对角线里面有没有皇后,我仅需拿这个位置的横纵坐标相加然后去数组找对应位置,如果是true,说明有皇后,如果是false,说明没有皇后。副对角线并不会出现负数的情况。因此只需要判断y+x在dig2是true还是false就行了。

在这里插入图片描述

class Solution {
    vector<vector<string>> ret;
    vector<string> path;
    bool checkCol[10],checkDig1[20],checkDig2[20];
    int _n;
public:
    vector<vector<string>> solveNQueens(int n) {
        _n=n;
        path.resize(n);
        for(int i=0;i<n;++i)
            path[i].resize(n,'.');

        dfs(0);
        return ret;   
    }

    void dfs(int row)
    {
        if(row == _n)
        {
            ret.push_back(path);
            return;
        }

        for(int col=0;col<_n;++col)
        {
            if(!checkCol[col] && !checkDig1[col-row+_n] && !checkDig2[col+row])
            {
                path[row][col]='Q';
                checkCol[col]=checkDig1[col-row+_n]=checkDig2[col+row]=true;
                dfs(row+1);
                checkCol[col]=checkDig1[col-row+_n]=checkDig2[col+row]=false;
                path[row][col]='.';
                
            }  
        }
    }
};

3.有效的数独

题目链接:36. 有效的数独

题目描述:

在这里插入图片描述

有效的数独,给一个9x9的格子,把数填满,其中每一行每一列以及3x3宫内,只能填1-9的数字,并且不能重复!

算法原理:
这里的思想和上面N皇后思想是一样的,采用类似哈希映射的方法。你让我判断一行有没有出现重复的元素,我可以搞一个bool类型的二维数组 bool row[9][10],前面9代表0~8行,后面多开一个空间 10个 里面有1~9的数字,row[3][7]=true 说明第三行7已经使用过了。
在这里插入图片描述
同理,这一列也搞一个bool 类型的二维数组,bool col[9][10],9代表0~8列,10代表有1 ~ 9,col[2][9]=true 代表第2列使用过9这个数字。

在这里插入图片描述
这个3x3的小格子,要么就是横着循环三次,竖着循环三次,但是这样太麻烦了。其实我们也可以搞一个哈希表把它存起来,让3行算作 一行,3列算作 一列。先搞出一个bool类型 bool grid[3][3] ,grid[0][0]代表第一个3x3的格子,grid[0][0]代表第二个3x3的格子,我们用3x3的数组就可以把所有小方格都表示出来了。然后我依旧要看每个3x3格子内数字是否重复,
在这里插入图片描述
因此再来一个10,搞成grid[0][0][10]的三维数组,来表示这里9个小方格,这里每个数映射到那个数组也非常好找,用这个数的下标/3,[x/3][y/3]就知道在那个小方格里了,然后10代表这个小方格里的1~9个数数字,grid[0][1][3] =true 表示第2个小放个里面3已经使用使用过了
在这里插入图片描述
因此我们就可以使用三个bool类型的数组,在O(1)的时间复杂度看一行一列一个小方格有没有出现重复数,这种就是典型的用空间换时间

class Solution {
    bool row[9][10];
    bool col[9][10];
    bool gids[3][3][10];
public:
    bool isValidSudoku(vector<vector<char>>& board) {
        for(int i=0;i<9;++i)
        {
            for(int j=0;j<9;++j)
            {
                if(board[i][j] != '.')
                {
                    int num=board[i][j]-'0';
                    if(row[i][num] || col[j][num] || gids[i/3][j/3][num])
                    	return false;
                    row[i][num]=col[j][num]=gids[i/3][j/3][num]=true;
                }
            }
        }
        return true;


    }
};

4.解数独

题目链接:37. 解数独

题目描述:

在这里插入图片描述

算法原理:
上面的是判断是否是有效数独,这里是填数独。这里还是用上面的三个bool类型数组,来判断这个数能不能放。这里我们一格一格的放,每个格子可以放1-9中其中一个数,但是肯定会是存在剪枝情况的。具体能不能放还是借助那三个bool类型数组来判断。我们递归就是拿着这个棋盘,开始依次遍历,看那个是空的就开始填,填的时候判断一下能填在填不能填就不填。然后能填递归到下一层,但是有可能这个能填的分支下面递归有的位置1 ~ 9都不能填的情况。因此这个分支可能是得不到正确结果的,那上面怎么知道你这种情况不行的呢?因此这个递归函数要有一个bool类型的返回值,当遇到某个格子1 ~ 9都不能填直接向上返回一个false,告诉它这个位置你填1不行,你要把这个位置填上2然后在往下试。递归函数参数只要把这个board给我就行了。bool dfs(board)

在这里插入图片描述

class Solution {
    bool row[9][10];
    bool col[9][10];
    bool grid[3][3][10];

public:
    void solveSudoku(vector<vector<char>>& board) {
        //初始化
        for(int i = 0; i < 9; ++i)
        {
            for(int j = 0; j < 9; ++j)
            {
           
               if(board[i][j] != '.')
               {
                    int num=board[i][j]-'0';
                    row[i][num]=col[j][num]=grid[i/3][j/3][num]=true;
               }
            }
        }

        dfs(board);
    }

    bool dfs(vector<vector<char>>& board)
    {
        for(int i = 0; i < 9; ++i)
        {
            for(int j = 0; j < 9; ++j)
            {
               if(board[i][j] == '.')
               {
                    //填数
                    for(int num = 1; num <= 9; ++num)
                    {
                        if(!row[i][num] && !col[j][num] && !grid[i/3][j/3][num])
                        {
                            board[i][j]='0'+num;
                            row[i][num]=col[j][num]=grid[i/3][j/3][num]=true;
                            if(dfs(board) == true) return true; //这个位置填的数已经是最终结果了,不要再往下试了
                            //恢复现场
                            board[i][j]='.';
                            row[i][num]=col[j][num]=grid[i/3][j/3][num]=false;
                        }
                    }
                    return false; //某个位置1~9都不能选,返回false
               }
            }
        }
        return true; //已经把数填完了,没有空位置了,返回true
    }
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1831127.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

开发框架表单设计器都有哪些突出的功能优势?

想要实现提质增效的办公效果&#xff0c;可以一起来聊聊低代码技术平台、开发框架表单设计器在职场办公中的应用价值吧。随着社会的进步和行业之间的竞争加剧化&#xff0c;要想更好地利用数据资源&#xff0c;更好地避免信息孤岛&#xff0c;提高部门之间的协作效率&#xff0…

618有什么好物分享 ?2024年最新数码榜单出炉

亲爱的朋友们&#xff0c;随着6.18购物狂欢节的临近&#xff0c;即将迎来一场购物盛宴。面对市场上琳琅满目的商品&#xff0c;团团知道大家在挑选时可能会感到困惑。因此&#xff0c;我根据个人的使用体验和深入的市场研究&#xff0c;为大家精心挑选了一系列高品质且性价比极…

2024爱分析·AI Agent创新成就奖开启申报丨奖项征集

AI Agent正成为企业数字化转型的关键力量。它们不仅提升了工作效率&#xff0c;优化了客户体验&#xff0c;更是在数据分析、决策支持和自动化流程中扮演着至关重要的角色。随着技术的不断进步和应用场景的拓展&#xff0c;AI Agent正以其独特优势&#xff0c;引领企业进入一个…

hive on spark 记录

环境&#xff1a; hadoop 2.7.2 spark-without-hadoop 2.4.6 hive 2.3.4 hive-site.xml <property><name>hive.execution.engine</name><value>spark</value> </property> <property><name>spark.yarn.jars</name>&l…

Ai绘画行业又叒翻天了!Stable Diffusion 3.0开源!多图实测附安装包!

千呼万唤始出来&#xff0c;期盼已久的SD3终于在6月12日开放了开源模型&#xff0c;本次开源的模型Stable Diffusion 3 Medium&#xff0c;是一个拥有 20 亿参数的SD3模型&#xff0c;其官网公布了它本次更新的特点&#xff1a; 还有更完整版本的大模型目前还未开放&#xff0c…

产品求职必备:“一份优秀产品简历的诞生”

​好不容易学成要开始求职&#xff0c;简历这一关却成了不少同学的“拦路虎”。 “我的简历投出去没反应~”“我的简历项目经验应该怎么写&#xff1f;” “我的简历完全不知道怎么改” 01明确职业目标 一份泛泛而谈的简历不会让你脱颖而出&#xff0c;如果你对自己还没有清晰…

flink1.12.0学习笔记(一)-部署与入门

flink1.12.0学习笔记&#xff08;1&#xff09;-部署与入门 1-1-Flink概述 Flink诞生 Flink 诞生于欧洲的一个大数据研究项目 StratoSphere。该项目是柏林工业大学的一个研究性项目。早期&#xff0c; Flink 是做 Batch 计算的&#xff0c;但在 2014 年&#xff0c; StratoS…

Chatgpt、Chatglm、Gemini、通义千问、文心一言、Kimi、字节豆包 AI 写高考作文,附各大模型体验案例~

六月&#xff0c;高考季&#xff0c;AI 来帮 阅读材料 要求&#xff1a;选准角度&#xff0c;确定立意&#xff0c;明确文体&#xff0c;自拟标题&#xff1b;不要套作&#xff0c;不得抄袭&#xff1b;不得泄露个人信息&#xff1b;不少于800字。 Ai 来写作 【构建提示…

网站的图片都是怎么处理的

我们平常见到的很多网站里面都有很多地图片&#xff0c;那么这些图片的文件是怎么处理的呢。图片是一个网站的重要元素之一&#xff0c;图片可以给用户直接的视觉冲击&#xff0c;好的图片则可以迎来不少的流量。图片有大有小&#xff0c;都是根据网站的局部需要而确定图片的尺…

安卓TextView控件实现下划线

效果展示 这里需要使用到LayerDrawable&#xff0c;对应于<layer-list>标签。在drawable目录下新建一个text_underline.xml文件&#xff0c;text_underline.xml的代码如下&#xff1a; <?xml version"1.0" encoding"utf-8"?> <layer-lis…

SOLIDWORKS Electrical线号编写规则

SOLIDWORKS Electrical 正版软件可以自动在原理图中生成线号&#xff0c;比如需要线号L1 L2 L3 R S T U V W &#xff0c;以及101 102 103 &#xff0c;COM1 COM2 COM3 以及让其偶数显示(00、02、04)等等&#xff0c;在格式编辑器中有很多已有的变量供用户使用&#xff0c;用户…

力扣每日一题 6/11 暴力搜索

博客主页&#xff1a;誓则盟约系列专栏&#xff1a;IT竞赛 专栏关注博主&#xff0c;后期持续更新系列文章如果有错误感谢请大家批评指出&#xff0c;及时修改感谢大家点赞&#x1f44d;收藏⭐评论✍ 419.甲板上的战舰[中等] 题目&#xff1a; 给你一个大小为 m x n 的矩阵 b…

GPT_AI高速发展中什么是Prompt提示词?

提示词&#xff08;Prompt&#xff09;是给大语言模型&#xff08;以下简称模型&#xff09;的输入文本&#xff0c;用于指定模型应该执行什么样的任务并生成什么样的输出。 提示词发挥了“提示” 模型 应该做什么的作用。设计高质量的提示词需要根据目标任务和模型能力进行精…

LeetCode题练习与总结:求根节点到叶节点数字之和--129

一、题目描述 给你一个二叉树的根节点 root &#xff0c;树中每个节点都存放有一个 0 到 9 之间的数字。 每条从根节点到叶节点的路径都代表一个数字&#xff1a; 例如&#xff0c;从根节点到叶节点的路径 1 -> 2 -> 3 表示数字 123 。 计算从根节点到叶节点生成的 所…

【django问题集】django.db.utils.OperationalError: (1040, ‘Too many connections‘)

一、报错内容 django.db.utils.OperationalError: (1040, Too many connections) 主要体现&#xff1a;就是请求不了后台&#xff0c;登录都登录不了。 二、代码优化 原生django配置的mysql连接是没有连接池的功能&#xff0c;会导致mysql连接创建过多导致连接数超过了mysql服…

网络安全:什么是SQL注入

文章目录 网络安全&#xff1a;什么是SQL注入引言SQL注入简介工作原理示例代码 攻击类型为什么SQL注入危险结语 网络安全&#xff1a;什么是SQL注入 引言 在数字化时代&#xff0c;数据安全成为了企业和个人最关心的问题之一。SQL注入&#xff08;SQL Injection&#xff09;是…

移动操作系统更新管理

移动操作系统更新管理是大多数移动设备管理&#xff08;MDM&#xff09;解决方案中提供的一项功能&#xff0c;它允许组织管理移动设备上的操作系统更新。MDM解决方案定期扫描设备以检查可用的移动操作系统更新&#xff0c;并根据配置的策略管理操作系统更新。操作系统更新管理…

vulnhub靶机hacksudoLPE中Challenge-2

二、Challenge-2 1. ar Abusing 这个是要利用suid注意sudo也可以用&#xff0c;但是还是按照要求来 注意使用的suid自然是home文件夹 2. ash abusing 33. atobm Abusing 环境有问题&#xff0c;做不了 34. base32 Abusing 35. bash Abusing 36. cat Abusing 37. chmod Abusin…

我一直看不明白:“C++会被java/python等这些语言替代”

在开始前刚好我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「C的资料从专业入门到高级教程」&#xff0c; 点个关注在评论区回复“888”之后私信回复“888”&#xff0c;全部无偿共享给大家&#xff01;&#xff01;&#xff01; 有些程序&#xff0c;是既可以…

ETL驱动企业集成转型与数据集成创新

数据集成&#xff1a;企业数智化的核心 数据集成是这一资产发挥价值的关键步骤&#xff0c;它将分散在不同来源的数据汇集到统一的平台&#xff0c;实现数据的集中管理和深入分析。通过这一过程&#xff0c;企业能够打破信息孤岛&#xff0c;提升数据的准确性和可靠性&#xf…