【DP】【构造】NOIp模拟题 演讲 题解
极其考思维的好题
题目背景
众所周知,$\mathrm{Zdrcl}$是一名天天$\mathrm{AK}$的高水平选手。
作为一民长者,为了向大家讲述自己$\mathrm{AK}$的经验,他决定在一个礼堂里为大家举办一场演讲。题目描述
这个礼堂拥有$N\times M$个位子,排成$N$行$M$列。每个位子都有一盏灯,一开始有的灯是亮的,有的灯是灭的。这个礼堂十分诡异,人们操作一次只能使某一行或某一列(某一行或某一列由操作者你自己来决定)的灯的明暗状态全都发生转变(显然,我们不一定可以把所有的灯都点亮)。
来听演讲的人只会坐在灯已经被点亮的位置, 所以可以听演讲的位置只会是一个只由灯是亮的的位子所组成的矩形(不然坐太乱,$\mathrm{Zdrcl}$会不高兴的) 。
$\mathrm{Zdrcl}$知道会有很多人来听演讲, 所以他希望找到一个经过若干操作后的面积最大的只由灯是亮的的位子所组成的矩形。 这个任务当然由想$\mathrm{AK}$的你来完成啦!
输入输出格式
输入格式:
第一行两个正整数表示$N,M$。
接下来有$N$行,每行有$M$个字符(‘#’表示这个灯初始状态是亮的,‘.’表示这个灯初始状态是暗的)。
输出格式:
一行一个整数表示你找到的矩形的面积。
输入输出样例
输入样例#1:
3 3
..#
##.
.#.输出样例#1:
6输入样例#2:
4 6
.#....
...###
.##.#.
...#..输出样例#2:
9说明
样例1解释
数据范围
对于$5\%$的数据:$N=2,M=2$
对于$15\%$的数据:$N\times M\le 8$
对于$30\%$的数据:$N,M\le 10$
对于$60\%$的数据:$N\le 1\le 10^2$
对于$80\%$的数据:$N\le 4\times 10^2$
对于$100\%$的数据:$N\le 2\times 10^3$
输入文件比较大, 请使用比较快速的读入方法。
提示
这一题写起来不是很困难。
题解:
这个题只要第一步想对了,剩下的DP部分就不难写。主要就是考虑怎么判断是否能全部点亮。
多次手玩可以发现对于可以被全部点亮的部分的特性。因为异或的逆运算还是异或,灯的开关就是在异或。因此我们考虑把矩阵转化为0和1。
上面提到灯的开关是进行了异或,因此对于任意行或列的操作,它们的顺序是可以被打乱的。我们假设先进行列操作,我们要尽可能把序列变为形如
00000
11111
11111
00000
这样,才能在之后只进行行操作时可以完成矩阵的变换。
那么上面给出的矩阵原来可能是这样的
01001
10110
10110
01001
可以发现,它们左右异或的结果总是一列均为1或一列均为0。因为如果一列均为1的话,那么只需要对其中一列进行反转即可;如果一列均为0的话,这两列就是一样的,可以对它们进行相同的操作而达到目的。
1101
1101
1101
1101
不过这样异或会使得矩阵的宽度减小1,我们只需要在计算的时候把这一维加上1就可以了,因为有$latex x$个异或结果,代表了$latex x+1$列。最后再单独处理最优解只占一列的特殊情况。
而有了这样的矩阵,我们的目的就是求最大子矩阵,其中每一列的数字都相同。这样用单调栈可以做到$latex O(nm)$。
当时出题人给出的解法是通过前5%的数据找规律,发现对于一个合法的矩阵,它内部的每一块2×2区域都满足“两种状态出现的次数都是偶数”。
即0出现0次,1出现4次/0出现4次,1出现0次/0出现2次,1出现2次。这样的话感觉条件变少了,不过正确性也可以保证,暂时不写代码。(咕
Code:
#include<cstdio>
#include<cstring>
char c[2222][2222];
int Xor[2222][2222];
int con[2222];
int q[2222],l=0,r=0;
int ext[2222];
int main()
{
int n,m;
scanf("%d%d",&n,&m);
for(int i=1;i<=n;++i)
scanf("%s",c[i]+1); int ans=1,tt=1;
for(int i=1;i<=n;++i)
{
tt=1;
for(int j=1;j<=m;++j)
if(c[i][j]==c[i][j-1])
{
++tt;
ans=ans>tt?ans:tt;
}
else
tt=1;
}
for(int i=1;i<=m;++i)
{
tt=1;
for(int j=1;j<=n;++j)
if(c[i][j]==c[i-1][j])
{
++tt;
ans=ans>tt?ans:tt;
}
else
tt=1;
}
for(int i=1;i<n;++i)
for(int j=1;j<=m;++j)
Xor[i][j]=(c[i][j]!=c[i+1][j]);
for(int i=1;i<=m;++i)
{
l=0,r=0;
for(int j=1;j<n;++j)
{
if(i==1||Xor[j][i]!=Xor[j][i-1])
con[j]=1;
else
con[j]++;
int cnt=0;
while(l<r&&con[j]<con[q[r]])
{
int tmp=(j-q[r]+1+ext[r])*(con[q[r]]);
ans=ans>tmp?ans:tmp;
cnt+=ext[r]+1;//好久没用单调栈做题了,忘记还要加上之前延伸的块……
--r;
}
q[++r]=j;
ext[r]=cnt;
}
for(int j=l+1;j<=r;++j)
{
int tmp=(n-q[j]+1+ext[j])*(con[q[j]]);
ans=ans>tmp?ans:tmp;
}
}
printf("%d\n",ans);
return 0;
}
【DP】【构造】NOIp模拟题 演讲 题解的更多相关文章
- 一些noip模拟题一句话题解
Problem A: 序列 Time Limit: 10 Sec Memory Limit: 256 MBSubmit: 12 Solved: 9[Submit][Status][Web Boar ...
- 【入门OJ】2003: [Noip模拟题]寻找羔羊
这里可以复制样例: 样例输入: agnusbgnus 样例输出: 6 这里是链接:[入门OJ]2003: [Noip模拟题]寻找羔羊 这里是题解: 题目是求子串个数,且要求简单去重. 对于一个例子(a ...
- NOIP模拟题汇总(加厚版)
\(NOIP\)模拟题汇总(加厚版) T1 string 描述 有一个仅由 '0' 和 '1' 组成的字符串 \(A\),可以对其执行下列两个操作: 删除 \(A\)中的第一个字符: 若 \(A\)中 ...
- 8.22 NOIP 模拟题
8.22 NOIP 模拟题 编译命令 g++ -o * *.cpp gcc -o * *.c fpc *.pas 编译器版本 g++/gcc fpc 评测环境 位 Linux, .3GHZ CPU ...
- 9.9 NOIP模拟题
9.9 NOIP模拟题 T1 两个圆的面积求并 /* 计算圆的面积并 多个圆要用辛普森积分解决 这里只有两个,模拟计算就好 两圆相交时,面积并等于中间两个扇形面积减去两个三角形面积 余弦定理求角度,算 ...
- noip模拟题题解集
最近做模拟题看到一些好的题及题解. 升格思想: 核电站问题 一个核电站有N个放核物质的坑,坑排列在一条直线上.如果连续M个坑中放入核物质,则会发生爆炸,于是,在某些坑中可能不放核物质. 任务:对于给定 ...
- NOIP模拟题17.9.26
B 君的任务(task)[题目描述]与君初相识,犹如故人归.B 君看到了Z 君的第一题,觉得很难.于是自己出了一个简单题.你需要完成n 个任务,第i 任务有2 个属性ai; bi.其中ai 是完成这个 ...
- PAT甲级 模拟题_C++题解
模拟题 PAT (Advanced Level) Practice 模拟题 目录 1008 Elevator (20) 1042 Shuffling Machine (20) 1046 Shortes ...
- 【noip模拟题】迎接仪式(dp+特殊的技巧)
好神的一题... 这是一道DP题,本题的难点在于状态的确定,由于调整是任意的,很难划分状态,我们略微修改一下调整的形式:把一次’j’和’z’交换看做两次变换:’j’->’z’;’z’->’ ...
随机推荐
- Python程序调试-TabError: inconsistent use of tabs and spaces in indentation
报错信息:TabError: inconsistent use of tabs and spaces in indentation 说明:代码缩进统一使用Tab键或空格键,不能混用. 解决办法: 1. ...
- jdbc中Statement和PreparedStatement有什么区别?哪个性能更好?
Statement和PreparedStatement的功能主要是对sql语句的执行 区别 (1)Statement每执行一条sql语句就需要生成一条执行计划,执行100条就需要100条执行计划Pre ...
- 学习Vue.js需要了解的部分内容
重要: 1.如果要通过js/模板引用 图片到项目,图片路径需要使用require. 2.$event: $event 等于$emit 抛出的值,还可以使用$event.target.value. $e ...
- 2.Books
Books示例说明了Qt中SQL类如何被Model/View框架使用,使用数据库中存储的信息,创建丰富的用户界面. 首先介绍使用SQL我们需要了解的类: 1.QSqlDatabase: QSqlDat ...
- Yii2中ACF和RBAC
ACF ( Access Control Filter) ACF ( Access Control Filter)官网的解释就是一个可以在模型或控制器执行行为过滤器,当有用户请求时,ACF将检查acc ...
- Celery笔记
异步任务神器 Celery 简明笔记 2016/12/19 · 工具与框架 · Celery, 异步 原文出处: FunHacks 在程序的运行过程中,我们经常会碰到一些耗时耗资源的操作,为了避 ...
- You-need-to-know-css
半透明边框 背景知识: background-clip <div class="main"> <input id="pb" type=&quo ...
- 使用Sqlserver事务发布实现数据同步(转)
出处:http://www.cnblogs.com/daizhj/archive/2009/11/18/1605293.html 事务的功能在sqlserver中由来已久,因为最近在做一个数据同步方案 ...
- LightOJ 1038 Race to 1 Again (概率DP,记忆化搜索)
题意:给定一个数 n,然后每次除以他的一个因数,如果除到1则结束,问期望是多少. 析:概率DP,可以用记忆公搜索来做,dp[i] = 1/m*sum(dp[j] + 1) + 1/m * (dp[i] ...
- 第18章-使用WebSocket和STOMP实现消息功能
Spring 4.0为WebSocket通信提供了支持,包括: 发送和接收消息的低层级API: 发送和接收消息的高级API: 用来发送消息的模板: 支持SockJS,用来解决浏览器端.服务器以及代理不 ...
