玉米田

原题

#include <cstring>
#include <iostream>
#include <algorithm>
#include <vector>using namespace std;const int N = 14, M = 1 << 12, mod = 1e8;int n, m;
int w[N];
vector<int> state;
vector<int> head[M];
int f[N][M];bool check(int state)
{//  return  !(state & state << 1);if ((state<<1)& state)return false; //移位后即变成相邻位置的元素比较,!=0的写法错误,因为 state是vector,不是数字
//  if ((state>>1)& state!=0)return false;return true;
}int main()
{cin >> n >> m;for (int i = 1; i <= n; i ++ )for (int j = 0; j < m; j ++ ){int t;cin >> t;w[i] += !t * (1 << j); //左移J位置,相加后得到一行的状态序列 }for (int i = 0; i < 1 << m; i ++ )if (check(i))state.push_back(i);  //记录可行状态,即相邻位置不能相同 for (int i = 0; i < state.size(); i ++ )for (int j = 0; j < state.size(); j ++ ){int a = state[i], b = state[j];if (!(a & b)) //i状态可以和J状态靠在一起 head[i].push_back(j);}f[0][0] = 1;for (int i = 1; i <= n + 1; i ++ ) //从第一行遍历到第n+1行 for (int j = 0; j < state.size(); j ++ ) //第i行遍历至状态为J if (!(state[j] & w[i]))  //第i行状态为J与当前行的状态比较 for (int k=0;k<head[j].size();k++)  //遍历J状态所有相邻状态 //for (int k : head[j]){int tp=head[j][k];f[i][j] = (f[i][j] + f[i - 1][tp]) % mod;}cout << f[n + 1][0] << endl;  //第n+1行 状态为0的总数 return 0;
}

炮兵阵地

原题

#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define maxr 110
#define maxc 15
#define maxm 70
#define CL(a) memset(a,0,sizeof(a))
bool legal(int a, int b) { return a & b; }
int row, col;
int nums;
int base[maxr];
int state[maxm], soldier[maxm];
int dp[maxr][maxm][maxm];//第i行为j状态,i-1行为k状态,最大炮兵个数dp[i][j][k]
int main()
{CL(base); CL(state); CL(soldier); CL(dp);nums = 0;char str[2][maxc];scanf("%d %d", &row, &col);for (int i = 0; i < row; i++)  //将地图转换成二进制{scanf("%s", str[0]);for (int j = 0; j < col; j++)if (str[0][j] == 'H') base[i] += 1 << j; //base[i]为第i行的地图}for (int i = 0; i < (1 << col); i++) {  //确立仅仅是两个炮兵互不攻击的状态if (legal(i, i << 2) || legal(i, i << 1)) continue; //相邻一位或者隔一位为相交int k = i;   while (k) {  //计算炮兵数量soldier[nums] += k & 1; k = k >> 1; //右移}state[nums] = i; //记录状态nums++;}for (int i = 0; i < nums; i++)  //初始化,nums为最大可能状态数量{if (legal(state[i], base[0])) continue; //去除炮兵在山上的dp[0][i][0] = soldier[i];  //0层,状态i,上一层状态0,等于状态i的炮兵数量}for (int r = 1; r < row; r++)  //每一行{for (int i = 0; i < nums; i++)  //第i行状态{if (legal(state[i], base[r])) continue; //r层状态i去除炮兵在山上的for (int j = 0; j < nums; j++) //第i-1行状态{if (legal(state[j], base[r - 1])) continue; //去除炮兵在山上的if (legal(state[i], state[j])) continue;  //除去上下两行相互攻击for (int k = 0; k < nums; k++) //第i-2行状态{if (r - 2 >= 0 && legal(state[k], base[r - 2])) continue; //去除炮兵在山上的if (legal(state[i], state[k])) continue;  //除去上下两行相互攻击if (legal(state[j], state[k])) continue;  //除去上隔一行下两行相互攻击dp[r][i][j] = max(dp[r][i][j], dp[r - 1][j][k] + soldier[i]);}}}}int ans = 0;for (int i = 0; i < nums; i++)for (int j = 0; j < nums; j++)ans = max(ans, dp[row - 1][i][j]);printf("%d\n", ans);return 0;
}

玉米田 炮兵阵地 状态压缩DP相关推荐

  1. POJ 1185 炮兵阵地(状态压缩DP)

    Description 司令部的将军们打算在N*M的网格地图上部署他们的炮兵部队.一个N*M的地图由N行M列组成,地图的每一格可能是山地(用"H" 表示),也可能是平原(用&quo ...

  2. POJ1185炮兵阵地(状态压缩 + dp)

    题目链接 题意:给出一张n * m的地图,其中 有的地方能放大炮,有的地方不能,大炮与上下左右两个单位范围内会相互攻击,问最多能放几个大炮 能放大炮为1不能放大炮为0,把每一行看做一个状态,要除去同一 ...

  3. 动态规划——状态压缩dp

    文章目录 概述 状态压缩 使用条件 状压dp 位运算 棋盘(基于连通性)类问题 概述 例题 蒙德里安的梦想 小国王 玉米田 炮兵阵地 集合类问题 概述 例题 最短Hamilton路径 愤怒的小鸟 总结 ...

  4. AcWing 327. 玉米田(状态压缩DP)

    AcWing 327. 玉米田(状态压缩DP) 一.问题 二.分析 1.思路 2.状态表示 3.状态转移 4.循环设计 5.初末状态 三.代码 一.问题 二.分析 1.思路 这道题与之前所讲解的AcW ...

  5. jzoj1768,P2704,POJ1185-[NOI2001]炮兵阵地【状态压缩dp】

    正题 POJ链接:http://poj.org/problem?id=1185 jzoj链接:https://jzoj.net/senior/#main/show/1768 洛谷评测记录:https: ...

  6. 327 玉米田(状态压缩dp)

    1. 问题描述: 农夫约翰的土地由 M×N 个小方格组成,现在他要在土地里种植玉米.非常遗憾,部分土地是不育的,无法种植.而且,相邻的土地不能同时种植玉米,也就是说种植玉米的所有方格之间都不会有公共边 ...

  7. 状态压缩DP AcWing算法提高课 (详解)

    基础课的状态压缩点这里 基础课中 蒙德里安的梦想 属于 棋盘式状态压缩dp,最短Hamilton路径 属于 集合状态压缩dp 1064. 小国王(棋盘式/基于连通性) 这种棋盘放置类问题,在没有事先知 ...

  8. 第一章 动态规划 状态压缩DP

    1.基本概述 状态压缩dp和状态机一样,都是一种特殊的状态表示方式.状态机用一系列小状态表示某一状态.状态压缩dp用二进制数进行表示.虽然看代码起来时间复杂度比较高,但是很多的情况都给剪枝掉了. 状态 ...

  9. 动态规划-状态压缩DP

    [SCOI2005] 互不侵犯 题目描述 https://www.luogu.com.cn/problem/P1896 在N×N的棋盘里面放K个国王,使他们互不攻击,共有多少种摆放方案.国王能攻击到它 ...

最新文章

  1. linux命令行安装使用KVM
  2. 【AWS 安全系列】Amazon S3 配置错误(下)
  3. Oracle 9i/10g/11g数据库升级路线图总览
  4. MySQL不能查看表_mysql root用户登录后无法查看数据库全部表
  5. Fomo3d常见问题
  6. Java学习笔记--继承和多态(下)
  7. 顶级投资者的21条箴言(组图)
  8. ubuntu 下系统监视器_Ubuntu下,用Pyinstaller打包桌面系统时,你踩坑了没?
  9. 逐渐摆脱高通和联发科!华为手机将采用更多麒麟芯片
  10. python调用百度地图实现导航pc_利用python和百度地图API实现数据地图标注
  11. SpringMVC_Controller注解与RequestMapping
  12. 图解WinHex使用入门
  13. mov格式如何转换成mp4?详细步骤教程
  14. JAVA习题001--产生多个随机数并使用冒泡排序将数字从小到大排序
  15. PC端页面如何调用QQ进行在线聊天?
  16. android如何增加北斗定位,安卓手机怎么设置北斗导航图文教程
  17. Java匿名内部类的用法(简单教学)
  18. 新建SVN仓库并上传项目
  19. centos7下升级GLIBC2.31
  20. 大数据立法 贵阳走在前列

热门文章

  1. 电脑启用网络发现以后在点开又成关闭状态了,导致网上邻居访问不了 。如何处理
  2. 中点画线法c语言程序,计算机图形学 :中点画圆法
  3. JavaScript对输入的用户名密码等进行判断
  4. 华硕笔记本能通用的BIOS型号
  5. 数图互通高校房产管理——房屋模拟分配建设
  6. Java Stream来写算法01——自幂数(水仙花数)
  7. Web前端HTML、CSS测试:世界地球日
  8. 为什么程序员要学linux?
  9. 加密算法之RSA算法
  10. win10 使用苹果耳机没有声音解决方案