#include<bits/stdc++.h> using namespace std; ; ; int a,b,n; int g[A][A],q[A][N],Q[A][N]; int head[A],tail[A]; int Head[A],Tail[A]; inline int read(){ ,f=;char ch=getchar(); ;ch=getchar();} )+(x<<)+(ch^);ch=getchar();} return x*f;} int main(){…
Solution 二维单调队列, 这个数组套起来看得我眼瞎... Code #include<cstdio> #include<algorithm> #include<cstring> #define rd read() #define rep(i,a,b) for(register int i = (a); i <= (b); ++i) #define per(i,a,b) for(register int i = (a); i >= (b); --i)…
1047: [HAOI2007]理想的正方形 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 2857  Solved: 1560[Submit][Status][Discuss] Description 有一个a*b的整数组成的矩阵,现请你从中找出一个n*n的正方形区域,使得该区域所有数中的最大值和最小值的差最小. Input 第一行为3个整数,分别表示a,b,n的值第二行至第a+1行每行为b个非负整数,表示矩阵中相应位置上的数.每行相邻两数之间…
题目链接 1047: [HAOI2007]理想的正方形 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 2369  Solved: 1266[Submit][Status][Discuss] Description 有一个a*b的整数组成的矩阵,现请你从中找出一个n*n的正方形区域,使得该区域所有数中的最大值和最小值的差最小. Input 第一行为3个整数,分别表示a,b,n的值第二行至第a+1行每行为b个非负整数,表示矩阵中相应位置上的数.每行相…
单调队列..先对每一行扫一次维护以每个点(x, y)为结尾的长度为n的最大最小值.然后再对每一列扫一次, 在之前的基础上维护(x, y)为结尾的长度为n的最大最小值. 时间复杂度O(ab) (话说还是deque2048ms快..list3572ms慢死了) #include<bits/stdc++.h> using namespace std; const int maxn = 1009; int X[maxn][maxn], R, C, N; int MN[maxn][maxn], MX[m…
题目链接:P2216 [HAOI2007]理想的正方形 题目描述 有一个 \(a\times b\)的整数组成的矩阵,现请你从中找出一个 \(n\times n\)的正方形区域,使得该区域所有数中的最大值和最小值的差最小. 输入格式 第一行为3个整数,分别表示a,b,n的值 第二行至第a+1行每行为b个非负整数,表示矩阵中相应位置上的数.每行相邻两数之间用一空格分隔. 输出格式 仅一个整数,为 \(a\times b\)矩阵中所有" \(n\times n\)正方形区域中的最大整数和最小整数的差…
题目链接:http://61.187.179.132/JudgeOnline/problem.php?id=1047 题意:给出一个n*m的矩阵.在所有K*K的子矩阵中,最大最小差值最小的是多少? 思路:枚举每一行,枚举每一列,(r,c),将(r-K+1,c-K+1)中的数字插入到单调队列中保存(这里设置两个单调队列,一个最大一个最小).每次计算以(r,c)为右下角的子矩阵的值时,判断队列头元素的列数是不是大于等于c-K+1,否则删掉队头.插入时,比如维护最小的单调队列,要判断队尾的元素是不是小…
开b组单调队列,分别维护此时某一列中的最大/最小值 然后我每次把它们的头取出来,塞到维护行的单调队列里,就是n*n的最大/最小值 #include<bits/stdc++.h> #define pa pair<int,int> #define CLR(a,x) memset(a,x,sizeof(a)) using namespace std; typedef long long ll; ; inline ll rd(){ ll x=;; ;c=getchar();} +c-',c…
题意很简明吧? 枚举的矩形下边界和右端点即右下角,来确定矩形位置: 每一个纵列开一个单调队列,记录从 i-n+1 行到 i 行每列的最大值和最小值,矩形下边界向下推移的时候维护一下: 然后在记录的每一列的最大值和最小值上,跑滑动窗口,即用单调队列维护区间 [ j-n+1 , j ] 的最大值和最小值: 相当于维护了一个矩形的最大值和最小值 #include<cstdio> #include<iostream> #include<queue> #define R regi…
题目链接 Solution MD,经过这道题,算是掌握单调队列了... 可以先预处理出点 \((i,j)\) 往上 \(n\) 的最大值和最小值. 然后再横着做一遍单调队列即可. Code #include<bits/stdc++.h> #define in(x) x=read(); #define ll long long #define N 1001 using namespace std; ll read() { char ch=getchar(); ll f=1,w=0; while(…
洛谷P2216 )逼着自己写DP 题意: 给定一个带有数字的矩阵,找出一个大小为n*n的矩阵,这个矩阵中最大值减最小值最小. 思路: 先处理出每一行每个格子到前面n个格子中的最大值和最小值.然后对每一列求出长度为n的前面算出来的最大值的最大值,前面算出来的最小值的最小值.如果直接做是n的三次方,但是用单调队列优化后就是n方的. #include <algorithm> #include <iterator> #include <iostream> #include &l…
Code: #include<cstdio> #include<queue> #include<algorithm> using namespace std; #define maxn 1002 #define ll long long #define inf 100000000000 int minv[maxn][maxn], maxv[maxn][maxn]; struct Node{ ll val; int pos; Node(ll val=0,int pos=0…
Description Orez很喜欢搜集一些神秘的数据,并经常把它们排成一个矩阵进行研究.最近,Orez又得到了一些数据,并已经把它们排成了一个n行m列的矩阵.通过观察,Orez发现这些数据蕴涵了一个奇特的数,就是矩阵中上下对称且左右对称的正方形子矩阵的个数. Orez自然很想知道这个数是多少,可是矩阵太大,无法去数.只能请你编个程序来计算出这个数. Input 文件的第一行为两个整数n和m.接下来n行每行包含m个正整数,表示Orez得到的矩阵. Output 文件中仅包含一个整数answer…
题目链接 首先可以想到路径一定是在直径上的. 然后对每个点dfs出不经过直径的以它开始的路径最大长度,记为dis 然后就可以求出直径之后枚举左右端点,设左端点l右端点r,直径上点距离直径上起点的距离用sum[]表示 则此时的$ans=max(max(sum[l],sum[End]-sum[r]),max(dis[i])l<=i<=r))$ 右面那个玩意可以单调队列维护. (然后我单调队列打反了变成维护最小值,GG.) #include<cstdio> #include<alg…
题目链接 首先这题可以肯定的是朴素DP秒出.然后单调队列优化因为没接触过所以不会emmm 而且脑补没补出来 坐等四月省选倒数第一emmm 心态爆炸,偷懒放题解链接 #include<cstdio> #include<cstring> #include<cctype> #include<cstdlib> #include<algorithm> #define maxn 2020 #define INF 0x7fffffff using namesp…
题目描述 现在有一堆数字共N个数字(N<=10^6),以及一个大小为k的窗口.现在这个从左边开始向右滑动,每次滑动一个单位,求出每次滑动后窗口中的最大值和最小值. 例如: The array is [1 3 -1 -3 5 3 6 7], and k = 3. 输入输出格式 输入格式: 输入一共有两行,第一行为n,k. 第二行为n个数(<INT_MAX). 输出格式: 输出共两行,第一行为每次窗口滑动的最小值 第二行为每次窗口滑动的最大值 输入输出样例 输入样例#1: 8 3 1 3 -1 -…
LINK:yyf hates choukapai 由于赶时间 要做的题有点小多.. 所以简略概述一下. 容易想到一个暴力dp \(f_{i,j,k}\)表示到了第i张牌此时连抽j次已经单抽k次的最大值. 转移可以刷表转移 复杂度O(1) 期望得分50. 考虑\(d==m\)时可以发现第三维可以直接去掉了 然后这样dp是\(s\cdot n\)的 加上 上面的做法 期望得分70. 考虑正解 状态都已经爆了 所以需要降维 考虑将第三维给扔掉. 那么如何满足限制?容易发现最优解中一定是一段单抽一段连抽…
首先得讲一下单调队列,顾名思义,单调队列就是队列中的每个元素具有单调性,如果是单调递增队列,那么每个元素都是单调递增的,反正,亦然. 那么如何对单调队列进行操作呢? 是这样的:对于单调队列而言,队首和队尾都可以进行出队操作,但只有队尾能够进行入队操作. 至于如何来维护单调队列,这里以单调递增队列为例: 1.如果队列的长度是一定的,首先判断队首元素是否在规定范围内,如果不再,则队首指针向后移动.(至于如何来判断是否在制定范围内,一般而言,我们可以给每个元素设定一个入队的序号,这样就能够知道每个元素…
2892: 强袭作战 Time Limit: 50 Sec  Memory Limit: 512 MBSubmit: 45  Solved: 30[Submit][Status][Discuss] Description 在一个没有冬马的世界里,经历了学园祭后的春希着急着想要见到心爱的雪菜.然而在排队想见雪菜的fans太多了,春希一时半会凑不到雪菜面前. 作为高帅富,这样的问题怎么能难倒春希?春希从武也手中拿到了取自金闪闪宝库里的多啦A梦的传话筒,并且给每一个排队的fans都发了一个传话筒. 于…
前言:把鸽了1个月的博客补上 ----------------- 题目链接 题目大意:机器人的灵敏性为$d$.每次可以花费$g$个金币来改造机器人,那么机器人向右跳的范围为$[min(d-g,1),max(d+g,x[n])]$.每个点都有分数$w[i]$.问至少花费多少金币得到分数$k$? 首先,如果用$g$个金币能满足条件,那么$g+1$也能.显然我们要最大值最小,所以我们不妨二分$g$,来求得满足条件的$g$的最小值. 普通的dp应该还是比较好写的.可以拿60pts. bool check…
显然的DP题..... 对于位置i,它由i-r~i-l的位置转移过来,容易得到方程 dp[i]=dp[i]+max(dp[i−r],...,dp[i−l]). 第一种:n2的暴力,只能拿部分分. 1 #include<bits/stdc++.h> 2 using namespace std; 3 const int N=2e5+5,inf=0x3f3f3f3f; 4 int n,l,r,a[N],dp[N],ans=-inf; 5 6 int main(){ 7 scanf("%d%…
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2216 那个关于位置的代价是带根号的,所以随着距离的增加而增长变慢:所以靠后的位置一旦比靠前的位置优,就会一直更优(因为距离相同地增长,基数大的增长慢),所以有决策单调性. 一开始写了和 bzoj 4709 一样的实现,就是使得队列里相邻两个位置的 “后一个位置优于前一个位置的时间” 是单调递增的.但是却 TLE .不知道为什么. #include<cstdio> #include<…
P2569 [SCOI2010]股票交易 题目描述 最近 \(\text{lxhgww}\) 又迷上了投资股票,通过一段时间的观察和学习,他总结出了股票行情的一些规律. 通过一段时间的观察,\(\text{lxhgww}\) 预测到了未来 \(T\) 天内某只股票的走势,第 \(i\) 天的股票买入价为每股 \(AP_i\)​,第 \(i\) 天的股票卖出价为每股 \(BP_i\)​(数据保证对于每个 \(i\),都有 \(AP_i \geq BP_i\)​),但是每天不能无限制地交易,于是股票…
从1开始,跳到比当前矮的不消耗体力,否则消耗一点体力,每次询问有一个步伐限制,求每次最少耗费多少体力 #include<cstdio> #include<cstring> #include<iostream> #include<algorithm> using namespace std; const int N=1e6+10; #define int long long int a[N],dp[N],q[N],l,r=1; int n,m,k; inlin…
刷水~ Code: #include<bits/stdc++.h> using namespace std; #define setIO(s) freopen(s".in","r",stdin) #define maxn 300000 #define inf 1000000 deque<int>p,q; struct Node { int x,y; }nd[maxn]; bool cmp(Node a, Node b) { return a.…
Code: #include<bits/stdc++.h> using namespace std; #define setIO(s) freopen(s".in","r",stdin) #define maxn 1002 #define inf 1000000000 deque<int>q; int n,m,A,B,C,D; int minv[maxn][maxn],sumv[maxn][maxn],val[maxn][maxn],tot[…
#include <iostream> #include <cstdio> #include <cstring> using namespace std; int n,L,R,a[400007]; const int INF=2e8+7; int dfs(int pos){ if(pos>n) return 0; int i,k=-INF; for(i=pos+L;i<=pos+R;++i){ k=max(k,dfs(i)); } return k+a[po…
理想的正方形 bzoj-1047 HAOI-2007 题目大意:有一个a*b的整数组成的矩阵,现请你从中找出一个n*n的正方形区域,使得该区域所有数中的最大值和最小值的差最小. 注释:$2\le a,b,n\le 10^3$,$n\le min(a,b)$. 想法:我的思路简直要死.通常的,我们优化暴力来完成对题目的求解.首先,想暴力.漂亮的暴力没想到,倒是想到一个a*b*n*n的,就是枚举每一个点,如果这个点可以作为n*n正方形的左上角,我就暴力枚举这个正方形的所有点.时间复杂度:O((a-n…
本文是笔者第二篇解题报告.从现在开始,会将练的一些题发到博客上并归类到"解题报告"标签中. 琪露诺是这样一道题 这道题可以用纯DP做,但是据说会超时.(为什么?看起来过河这题比它数据大多了)于是到Luogu题解上找到了单调队列优化. 首先讲一下纯DP思路 假设我们的⑨正在河中央,编号为i的格子上. 观察琪露诺的移动规律可得,琪露诺再往下走只能走到编号为i + l 到 i + r 之间的格子上. 于是想到,琪露诺之所以现在能在这里,一定是上一步从编号为 i - r 到 i - l 的格子…
https://www.luogu.org/problemnew/show/P1776 单调队列+多重背包的讲解https://www.cnblogs.com/JoeFan/p/4165956.html         https://blog.csdn.net/flyinghearts/article/details/5898183 #include<iostream> #include<algorithm> #include<deque> using namespa…