【算法笔记】分支限界专题

分支限界

整体结构

本质上感觉还是遍历解树+剪枝,但是配合优先队列使用以后可以更好的找到最优解。

例题

P8011 ⾛迷宫

对于迷宫问题,某一节点的关联节点指的是它四个方向上相邻的节点。

要利用flag数组确保不会重复访问。

 void bfs(){//1、初始化队列queue ,将第一个节点放入队列 t++; q[t].x = 1;q[t].y = 1;q[t].step = 0;flag[1][1] = true;//2.循环遍历队列while(h <= t){ //队列不空 // 3.取出队头,存入curNode cur = q[h]; h++;// 4. 利用产生式规则,拓展cur的关联节点入队for(int i = 0; i < 4; i++) { //四个方向拓展int nx = cur.x + z[0][i];int ny = cur.y + z[1][i];if(nx < 1 || nx > n || ny < 1 || ny > m) continue;//越界 if(a[nx][ny] == 1) continue; //有墙 if(flag[nx][ny]) continue; //走过 // 如果找到答案,结束搜索if(nx == n && ny == m){ans = cur.step + 1;//拓展出的节点到了终点,所以要把最后一步加上return ;}//既没跳过也没到终点,那就先存起来flag[nx][ny] = true;//拓展的过程中就已经用过t++;//存起来只是为了继续拓展q[t].x = nx;q[t].y = ny;q[t].step = cur.step + 1;}} } 

P8012 01背包

核心在于选和不选两个分支的剪枝,总体框架依然是取队头-判断剪枝-拓展-判断剪枝-入队。

 void bfs(){//1、初始化队列queue ,将第0个物品放入队列 t++;q[t].i = 0; //第0个物品 q[t].cp = 0;q[t].cv = 0;bestp = 0; //2.循环遍历队列while(h <= t){ //队列不空 // 3.取出队头,存入curNode cur = q[h];h++;int n_i = cur.i+1;if(n_i > n) continue;//物品用完了// 4. 利用产生式规则,拓展cur的关联节点入队// 选择下一个物品,并入队 if(cur.cv + items[n_i].volume <= V){ //装不下则剪掉选择该物品的分支t++;q[t].i = n_i;q[t].cp = cur.cp + items[n_i].price;q[t].cv = cur.cv + items[n_i].volume;bestp = max(bestp,q[t].cp);} // 计算上界double b = bound(n_i + 1, cur.cv, cur.cp);// 不选择下一个物品,且上界大于当前最佳解时,才将节点入队if (b > bestp) {t++;q[t].i = n_i;q[t].cp = cur.cp;q[t].cv = cur.cv;   }} } 

把手动固定队列换成优先队列的版本。由于优先队列会把价值密度更高的物品推到前面,所以程序会优先沿着局部最优的路径往下走,更便于找到最优路径。

 // 更快找到最优解:先探索最有希望的节点(即优先级最高的节点)// 更有效的剪枝:优先处理那些最有可能导致最优解的节点。double bound(int i, int cv, int cp) { double maxp = cp;int totv = cv;// 使用贪心策略继续添加物品while (i <= n && totv + items[i].volume <= V) {totv += items[i].volume;maxp += items[i].price;i++;}// 如果还有剩余空间,则按比例取最后一个物品的价值if (i <= n) {maxp += (V - totv) * (items[i].density);}return maxp;  }void bfs(){//1、初始化队列queue ,将第0个物品放入队列 Node cur;priority_queue<Node> p_q;cur.i = 0; //第0个物品 cur.cp = 0;cur.cv = 0;cur.ub  = bound(cur.i+1, cur.cv, cur.cp);//计算上界值 p_q.push(cur); //插入优先队列 //2.循环遍历队列while(!p_q.empty()){ //队列不空 // 3.取出队头,存入curcur = p_q.top();p_q.pop();int n_i = cur.i+1;if(n_i > n) continue;// 4. 利用产生式规则,拓展cur的关联节点入队// 选择下一个物品,并入队 if(cur.cv + items[n_i].volume <= V){ // 左剪枝 Node t;t.i = n_i;t.cp = cur.cp + items[n_i].price;t.cv = cur.cv + items[n_i].volume;t.ub  = bound(cur.i+1, cur.cv, cur.cp);//计算上界值 bestp = max(bestp,t.cp);p_q.push(t); //插入优先队列 } // 不选择下一个物品,并入队 // 计算上界Node t2;t2.i = n_i;t2.cp = cur.cp;t2.cv = cur.cv;t2.ub  = bound(cur.i+1, cur.cv, cur.cp);//计算上界值 if (t2.ub > bestp) {p_q.push(t2); //插入优先队列 }} } 

P8013 任务分配

总体框架不变,确定下界的自定义函数变了,多了一个枚举任务的逻辑,多了一个任务分配状态的记录,其他就比较常规啦。

 void bound(Node &e){//当前还有可能得到的最小代价int minsum = 0;for(int i = e.i + 1; i <= n; i++){ // 枚举人 int min_v = 2e9;// 贪心 for(int j = 1; j <= n; j++){ // 枚举任务 if(e.used[j] == 0 && a[i][j] <= min_v)min_v = a[i][j];}minsum += min_v;} e.lb = e.cost + minsum;} ​void bfs(){// 定义一个优先队列 priority_queue<Node> p_q;Node cur,next;cur.i = 0; //根节点cur.cost =0;cur.used.resize(n+10);cur.ve.resize(n+10);bound(cur);p_q.push(cur); //根节点入队 while(!p_q.empty()){ // 队列不为空 cur = p_q.top();p_q.pop();for(int j = 1; j <= n; j++){ //枚举任务 if(cur.used[j] == 1) continue; //任务被分配过 next.i = cur.i + 1;next.used = cur.used;next.ve = cur.ve;next.used[j] = 1;next.ve[next.i] = j; //第i个人,被分配了第j个任务 next.cost = cur.cost + a[next.i][j];bound(next);//计算下界 if(next.lb < ans){//剪枝 if(next.i == n){//更新最优解 if(next.cost < ans){ans = next.cost; }   }else{//入队 p_q.push(next); }}}}   }

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

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

相关文章

重写equals方法为什么还要重写hashcode方法?

目录 什么是 hashcode&#xff08;哈希码、散列码&#xff09;&#xff1f; 为什么 equals() 方法要重写&#xff1f; hashCode() 与 equals() 的关系 重写equals方法为什么还要重写hashcode方法&#xff1f; 什么是 hashcode&#xff08;哈希码、散列码&#xff09;&#…

python爬虫之线程与多进程知识点记录

一、线程 1、概念 线程 在一个进程的内部&#xff0c;要同时干多件事&#xff0c;就需要同时运行多个“子任务”&#xff0c;我们把进程内的这些“子任务”叫做线程 是操作系统能够进行运算调度的最小单位。它被包含在进程之中&#xff0c;是进程中的实际运作单位。一条线程指…

DAY01_Spring—Spring框架介绍IOCSpring工厂模式

目录 1 什么是框架2 Spring框架2.1 Spring介绍2.2 MVC模型说明2.3 IOC思想2.3.1 问题说明2.3.2 IOC说明 3 Spring IOC具体实现3.1 环境准备3.1.1 关于JDK说明3.1.2 检查JDK环境配置 3.2 创建项目3.3 关于Maven 命令3.3.1 install 命令3.3.2 clean 命令 3.4 添加jar包文件3.4.1 …

flutter使用getx进行数据状态管理,实现页面响应式

无论是什么样的应用&#xff0c;都还是需要最基础的数据来支撑的&#xff0c;而且不同的页面之间可能需要共享数据状态&#xff0c;这就显得数据状态管理非常有必要了。因为我这里使用了get依赖库&#xff0c;所以就可以直接在项目中使用getx来管理状态&#xff0c;不想再使用别…

【笔记】软件下载链接汇总

&#x1f388;欢迎加群交流&#x1f388; ✨✨✨https://ling71.cn/hmf.jpg✨✨✨ 浏览器历史版本下载 Firefox史版本下载&#xff1a;&#xff08;官网&#xff09; http://ftp.mozilla.org/pub/mozilla.org//firefox/releases/ Chrome历史版本、ChromeDriver历史版本&#x…

服务器机房上架交付流程

服务器上架交付 服务器到货验收后&#xff0c;会进行机房机房上架&#xff0c;完成重装系统、网络配置后交付使用 1、到货验收 采购服务器到货后&#xff0c;会联合多部门进行SN、配置、数量等多方面验收&#xff0c;如数量是否匹配&#xff0c;配置是否相符等也会拆开机箱看看…

Python基础知识:整理10 异常相关知识

1 异常的捕获 1.1 基础写法 """基本语法&#xff1a;try:可能发生错误的代码except:如果出现异常&#xff0c;将执行的代码""" try:fr open("D:/abc.txt", "r", encoding"utf-8") except:print("出现异常…

APM传感器校准

文章目录 前言一、校准加速度计二、校准罗盘三、校准陀螺仪四、校平地平线 前言 固件&#xff1a;rover 4.2.3 地面站&#xff1a;独家汉化版QGC 一、校准加速度计 点击左上角软件图标-》载具设置-》传感器-》加速度计 飞控方向默认为None即可&#xff0c;点击确定 点击确…

德语怎么翻译,中文翻译成德文有何要求?

近年来&#xff0c;随着中德之间的贸易往来日益频繁&#xff0c;德语翻译需求在市场上持续升温。那么&#xff0c;如何做好德语翻译&#xff0c;特别是将中文翻译成德文需要注意哪些要求呢&#xff1f; 首先&#xff0c;深入理解中文原文的语境和含义至关重要。中文含蓄且抽象&…

存储的基本架构

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 一、存储的需求背景二、自下而上存储架构总结 一、存储的需求背景 1、人的身份信息需要存储 这种信息可以用关系型数据库&#xff0c;例如mysql&#xff0c;那种表…

c++的宏举例和理解

宏提供了一种机制&#xff0c;能够使你在编译期替换代码中的符号或者语句。当你的代码中存在大量相似的、重复的代码时&#xff0c;使用宏可以极大的减少代码量&#xff0c;便于书写。 // 定义圆周率 #define PI 3.14159265 // 定义一个空指针 #define NULL ((void*)0) // 定…

第十二章 Java内存模型与线程(二)

文章目录 12.4 Java与线程12.4.1 线程的实现12.4.2 Java线程调度12.4.3 状态转换 12.4 Java与线程 12.4.1 线程的实现 实现线程主要有三种方式&#xff1a;使用内核线程实现&#xff08;1&#xff1a; 1 实现&#xff09;&#xff0c;使用用户线程实现&#xff08;1&#xff…

CMake入门教程【高级篇】自定义的构建命令add_custom_command

文章目录 1.概述信息2.命令作用3.完整代码示例4. 实际使用中的技巧1.概述信息 add_custom_command是一个非常强大的工具,它允许用户定义在构建过程中执行的自定义命令。这可以用于生成源文件、执行前后处理步骤、自动化测试等。 #mermaid-svg-9icMsOnoxbNTRCu0 {font-family:…

A Charming Algorithm for Count-Distinct

如何估计不重复元素的个数 本文提出一种很有趣的算法&#xff0c;估计一个数列里面不重复元素的个数&#xff0c;关键是它只使用指定大小的内存。 I recently came across a paper called Distinct Elements in Streams: An Algorithm for the (Text) Book by Chakraborty,…

FFmpeg 入门

1. 编译 参考文档&#xff1a;FFmpeg编译和集成(FFmpeg开发基础知识)&#xff0c;重点注意这句话&#xff1a; 在MSYS2 Packages可以查到云仓库有哪些包&#xff0c;直接安装可节约大量时间。 注意&#xff1a;这个路径可自定义 吐槽 在看到这篇文章之前&#xff0c;花了大…

腾讯云服务器购买指南,2024更新购买步骤

腾讯云服务器购买流程很简单&#xff0c;有两种购买方式&#xff0c;直接在官方活动上购买比较划算&#xff0c;在云服务器CVM或轻量应用服务器页面自定义购买价格比较贵&#xff0c;但是自定义购买云服务器CPU内存带宽配置选择范围广&#xff0c;活动上购买只能选择固定的活动…

【银行测试】银行项目,信用卡业务测试+常问面试(三)

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 银行测试-信用卡业…

产品经理之基础必备知识点

目录 前言 一.用户画像 1.1含义 1.2 举例说明 二.MVP&#xff08;最小可行产品&#xff09; 1.1含义 1.2 优缺点 三.体验地图 3.1 含义 3.2 举例说明 四.产品路线图 4.1 含义 4.2 举例说明 五.用户故事 5.1 含义 5.2 举例 六.用户故事地图 七.敏捷开发 7.1 含义 7.2 …

C++I/O流——(3)文件输入/输出(第二节)

归纳编程学习的感悟&#xff0c; 记录奋斗路上的点滴&#xff0c; 希望能帮到一样刻苦的你&#xff01; 如有不足欢迎指正&#xff01; 共同学习交流&#xff01; &#x1f30e;欢迎各位→点赞 &#x1f44d; 收藏⭐ 留言​&#x1f4dd; 含泪播种的人一定能含笑收获&#xff…

[M链表] lc82. 删除排序链表中的重复元素 II(单链表+好题+模拟)

文章目录 1. 题目来源2. 题目解析 1. 题目来源 链接&#xff1a;82. 删除排序链表中的重复元素 II 相似题目&#xff1a;[E链表] lc83. 删除排序链表中的重复元素(单链表模拟) 2. 题目解析 这个题目与 83 题都很类似&#xff0c;一个是将重复元素全部删除&#xff0c;另一个…