简单状压dp(以力扣464为例)

目录

1.状态压缩dp是啥?

2.题目分析

3.解题思路

4.算法分析

5.代码分析

6.代码一览

7.结语


1.状态压缩dp是啥?

顾名思义,状态压缩dp就是将原本会超出内存限制的存储改用更加有效的存储方式。简而言之,就是压缩dp的空间。

举个例子:假设这里有3盏灯,每盏灯的状态只有开和关。请问不改变顺序的前提下开关这些灯,有多少种情况。这里假设0是关闭,1是开启,那么等就有以下八种情况:

如果我们用字符串存储,就需要八个三长度的字符串。但是,我们可以把这些状态看作2进制的序列,那么我们使用一个数字7就可以保存这八种状态,比如数字4转化为二进制就是100,数字1就是001,这就是一种典型的状态压缩。

所以学习状压dp需要一定的位运算的基础哈。


2.题目分析

拿到题面我们要先对数据量进行分析,这里最多是有20个数据,那么比赛中所有可能的情况就是2的20次方种,我们这里是可以进行搜索的。


3.解题思路

我们看题面中给的数字个数有20个,我们就可以使用20位2进制存储排列的情况。然后我们简单的模拟一下游戏过程。假设10有个数:

  • 过程1:

        玩家1:2

        玩家2:3

        玩家1:4

        玩家2:5

        玩家1:?

  • 过程2:

        玩家1:4

        玩家2:3

        玩家1:2

        玩家2:5

        玩家1:?

我们分析一下这两个过程,我们玩家1到达“?”处时,剩余的数字和可选的数字都是一样的,所以这两个情况的结局是一样的。这里可以推理出,如果我们不做任何处理,就会产生大量的重复搜索,所以这里可以使用记忆化搜索或者dp等解题。


4.算法分析

因为本文章讲的是状压dp,所以这里我们选择使用dp进行搜索。这里有n个数字,那么会有2的n种情况,我们计算一下2的20次方个int变量没有超出内存,所以我们可以定义一个数组用来存储搜索过的情况,我们进行搜索的时候,再与这里的状态进行交互。


5.代码分析

int state=(1<<(maxChoosableInteger+1))-1;
vector<int> dp(state+1);

这里题面中的maxChoosableInteger是可以选择的数字个数,这里创建的state代表数字选择的状态,dp就是每个状态下的胜负情况,题目中是需要我们判断先手是不是必胜,所以我们只需要找到一条可以必胜的路线就可以了,如果所有路线都不能胜利,那么就是失败。

    bool canIWin(int maxChoosableInteger, int desiredTotal){if(desiredTotal==0)return true;if(maxChoosableInteger*(maxChoosableInteger+1)/2<desiredTotal)return false;int state=(1<<(maxChoosableInteger+1))-1;vector<int> dp(state+1);return f(desiredTotal,state,dp,maxChoosableInteger);}

上面的这个代码中有两个if,这里是进行特殊判断的,因为如果一开始的数字就是0,就直接判断胜利,因为你不论选择什么数字都可以超过0,下面的if是判断这局的所有和是否可以达到目标值,如果所有的值相加都无法达到目标值,那么就没有胜利者,既然没有胜利者,也就没有所谓的必胜策略。

下面的f就是我们的搜索函数

    bool f(int last,int state,vector<int>& dp,int n){if(last<=0)return false;if(dp[state]!=0){return dp[state] == 1;}bool ret=false;for(int i=1;i<=n;i++){if(((1<<i)&state) && !f(last-i,state^(1<<i),dp,n)){ret=true;break;}}dp[state]= ret ? 1 : -1;return ret;}

这里的last是上次选择后距离目标数的距离,state是数字选择的状态,这里的n就是可以选择的数字的最大值。这里我们采用的递归写法,在这个函数中,我们的两个玩家互相改变先手,什么意思呢?就是当我选完了一个数字,轮到另一个玩家选,那么就相当于剔除了一个数字和改变了目标值的新游戏的先手。所以,当这里递归发现last<=0了说明上一个玩家胜利了,这个玩家就失败了。

下面的if就是判断这个情况有没有被搜索过,如果dp[state]!=0说明这个情况已经被搜索过了,我们直接返回就行,这里我定义1就是胜利-1就是失败,所以这里判定如果是1就返回true。

接下来的for循环之前,我们先假设这次比赛是失败的,然后遍历每一种情况,这里首先需要判断,这个数字没有选择过,只需要判断state上的第i位是不是1就可以了,当然我们还需要判断,下一位玩家是不是失败,这里我们last减去我们选择的数字,然后更新state的状态,如果下手是失败的,那么就可以判断我们本次是成功的。所以ret变为true退出循环。

最后更新dp[state]的值,如果ret是true就赋值为1,否则赋值为-1。保存完毕后返回ret的值就完成了搜索。


6.代码一览

class Solution 
{
public:bool f(int last,int state,vector<int>& dp,int n){if(last<=0)return false;if(dp[state]!=0){return dp[state] == 1;}bool ret=false;for(int i=1;i<=n;i++){if(((1<<i)&state) && !f(last-i,state^(1<<i),dp,n)){ret=true;break;}}dp[state]= ret ? 1 : -1;return ret;}bool canIWin(int maxChoosableInteger, int desiredTotal){if(desiredTotal==0)return true;if(maxChoosableInteger*(maxChoosableInteger+1)/2<desiredTotal)return false;int state=(1<<(maxChoosableInteger+1))-1;vector<int> dp(state+1);return f(desiredTotal,state,dp,maxChoosableInteger);}
};

7.结语

简单状态压缩dp就讲到这里了哈,如果本文有什么错误的地方欢迎大家前来指正呀。

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

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

相关文章

jdk中自带的并发类

1、seamplore 信号量 countDownLaunch&#xff1a;等待所有线程都完成&#xff0c;主线程在执行 CyclicBarrirer 内存屏障 exchanger 线程之间交换数据 phaser 阶段协同器 阻塞队列

AWS-WAF-Log S3存放,通过Athena查看

1.创建好waf-cdn 并且设置好规则和log存储方式为s3 2. Amazon Athena 服务 使用 &#xff08;注意s3桶位置相同得区域&#xff09; https://docs.aws.amazon.com/zh_cn/athena/latest/ug/waf-logs.html#waf-example-count-matched-ip-addresses 官方文档参考,建一个分区查询表…

C. Earning on Bets

题目 个人补充&#xff1a; #include <bits/stdc.h> using namespace std; #define int long long #define pb push_back #define fi first #define se second #define lson p << 1 #define rson p << 1 | 1 #define ll long longconst int maxn 1e6 5, in…

C语言 | Leetcode C语言题解之第228题汇总区间

题目&#xff1a; 题解&#xff1a; char** summaryRanges(int* nums, int numsSize, int* returnSize) {char** ret malloc(sizeof(char*) * numsSize);*returnSize 0;int i 0;while (i < numsSize) {int low i;i;while (i < numsSize && nums[i] nums[i …

算法通关:004_1选择排序

代码一定要自己手敲理解 public class _004 {//选择排序&#xff0c;冒泡排序&#xff0c;插入排序//交换public static void swap(int[] arr,int i ,int j){int temp arr[i];arr[i] arr[j];arr[j] temp;}//选择排序public static void selectSort(int[] arr){if(arr null…

YOLOv10改进 | Conv篇 | 利用FasterBlock二次创新C2f提出一种全新的结构(全网独家首发,参数量下降70W)

一、本文介绍 本文给大家带来的改进机制是利用FasterNet的FasterBlock改进特征提取网络&#xff0c;将其用来改进ResNet网络&#xff0c;其旨在提高计算速度而不牺牲准确性&#xff0c;特别是在视觉任务中。它通过一种称为部分卷积&#xff08;PConv&#xff09;的新技术来减少…

NLP入门——词袋语言模型的搭建、训练与预测

卷积语言模型实际上是取了句子最后ctx_len个词作为上下文输入模型来预测之后的分词。但更好的选择是我们做一个词袋&#xff0c;将所有分词装在词袋中作为上下文&#xff0c;这样预测的分词不只根据最后ctx_len个分词&#xff0c;而是整个词袋中的所有分词。 例如我们的序列是&…

javaweb图书商城系统带万字文档网上书城java项目java课程设计java毕业设计

文章目录 图书商城系统一、项目演示二、项目介绍三、万字项目文档四、部分功能截图五、部分代码展示六、底部获取项目源码带万字文档&#xff08;9.9&#xffe5;带走&#xff09; 图书商城系统 一、项目演示 网上书城 二、项目介绍 语言&#xff1a;java 数据库&#xff1a;…

typora 两边太宽,设置宽度

步骤&#xff1a; 查看目前使用主题类型 文件 —> 偏好设置 —> 外观 —> 打开主题文件夹 修改对应的主题&#xff1a;max-width

MySQL 数据库支持存储emoji表情

当你通过node.js&#xff0c;往mysql存储emoji表情的时候&#xff0c;可能会遇到报错&#xff1a; code: ‘ER_TRUNCATED_WRONG_VALUE_FOR_FIELD’, errno: 1366, sqlMessage: “Incorrect string value: ‘\xF0\x9F\x8D\x94’ for column ‘nick_name’ at row 1”, sqlState…

MySQL数据库主从复制+mycat读写分离+MHA实操

目录 一、主从复制 1.1 主从复制简介 1.2 MySQL支持的复制类型 1.3 主从复制的工作过程 1.4 主从复制的同步模式 1.4.1 异步复制&#xff08;Asynchronous replication&#xff09; 1.4.2 全同步复制&#xff08;Fully synchronous replication&#xff09; 1.4.3 半同…

力扣2356.二维差分模板——子矩阵元素加1

力扣2356.二维差分模板——子矩阵元素加1 模板题 最后将n2*n2的矩阵删去周围一圈变成n*n矩阵的操作 class Solution {public:vector<vector<int>> rangeAddQueries(int n, vector<vector<int>>& queries) {vector<vector<int>> res…

【JavaWeb程序设计】Servlet(二)

目录 一、改进上一篇博客Servlet&#xff08;一&#xff09;的第一题 1. 运行截图 2. 建表 3. 实体类 4. JSP页面 4.1 login.jsp 4.2 loginSuccess.jsp 4.3 loginFail.jsp 5. mybatis-config.xml 6. 工具类&#xff1a;创建SqlSessionFactory实例&#xff0c;进行 My…

UI设计工具选择指南:Sketch、XD、Figma、即时设计

在数字产品设计产业链中&#xff0c;UI设计师往往起着连接前后的作用。产品经理从一个“需求”开始&#xff0c;制定一个抽象的产品概念原型。UI设计师通过视觉呈现将抽象概念具体化&#xff0c;完成线框图交互逻辑视觉用户体验&#xff0c;最终输出高保真原型&#xff0c;并将…

threadx netxduo stm32f407上实现http server

这次用的是CubeIDE CubeMX 要把NX_APP的mem分配的大一些&#xff0c;在app_azure_rtos.c中&#xff0c;我给的是40*1024&#xff0c;如果给的不够&#xff0c;会导致后面无法分配pool和thread等等 需要用到filex 要在CubeMX里面勾选上&#xff0c;还要用到http_server和dhcp …

1. InternLM - 入门岛

第1关 Linux 基础知识 1. 完成SSH连接与端口映射并运行hello_world.py SSH连接配置 # wsl2中生成密钥对&#xff08;~/.ssh/id_rsa, ~/.ssh/id_rsa.pub&#xff09; ssh-keygen -t rsa# 将id_rsa.pub在internStudio作为公钥导入SSH登录 $ ssh -p 38871 rootssh.intern-ai.o…

汽车免拆诊断案例 | 奥迪 Q7 e-tron无法通过插电式充电器充电

故障现象 车主反映&#xff0c;车辆无法使用自带的插电式充电器充电。&#xff08;这种充电方法是“Mode 2充电”&#xff0c;3针插头&#xff0c;10 A&#xff0c;2.2 kW&#xff09; 接车后验证故障&#xff0c;将Type 2充电插头连接到车辆时&#xff0c;充电口锁定销循环三…

3DSC(3D形状上下文特征)

形状上下文(shape context简写为SC)由Serge Belongie等人于2002年首次提出,是一种很流行的二维形状特征描述子,多用于目标识别和形状特征匹配。 2004年,Andrea Frome等人将形状上下文的工作从二维数据迁移到三维数据上提出了3D形状上下文(3DSC) 原理解析 2DSC的算法流程…

Git的基本知识点 + GitBash安装Pacman + Git命令含有中文,终端输出中文乱码

Git的基本知识点&#xff1a;整理自以下作者的文章繁华似锦Fighting的文章https://www.jianshu.com/nb/49854893另外还补充了git ls-file、.gitignore 等内容&#xff0c;涉及具体操作&#xff0c;还有命令总结。简略版可以看以上作者的文章&#xff0c;详细版可以看网盘里面的…

【STM32学习】stm32cubemx基础配置,点亮/闪烁一个LED灯

1、cubemx开始 打开cubemx&#xff0c;在help栏中&#xff0c;点击&#xff0c;选择安装你所需要的stm32芯片版本&#xff0c; 打开后&#xff0c;选择你所配置的芯片型号&#xff0c;如我配置的是stm32f4系列&#xff0c;勾选&#xff0c;点击Install。 安装好后&#xff0c;…