题解:CF1720E Misha and Paintings
题目传送门
题意
给定一个大小为
思路
首先先分类讨论,我们设
而如果
首先,令左上角
下面附上一张图方便理解:
那么我们只需要确定当前矩阵能不能用一次操作解决就行了。这个比较简单。我们先预处理处包含每种颜色所需的最小矩形的左上角和右上角。我们每次统计以
代码:
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int N=1010;
const int M=1010101;
ll n,m,num;
ll a[N][N],vis[M],maxni[M],maxnj[M],minni[M],minnj[M];
ll sum[N][N];
int main(){
ios::sync_with_stdio(false);
cin.tie(0);cout.tie(0);
cin>>n>>m;
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
cin>>a[i][j];
vis[a[i][j]]++;
}
}
for(int i=1;i<=n*n;i++)minni[i]=minnj[i]=n+1;
for(int i=1;i<=n*n;i++)if(vis[i])num++;
if(num<=m){
cout<<m-num;
return 0;
}
for(ll i=1;i<=n;i++){
for(ll j=1;j<=n;j++){
ll x=a[i][j];
maxni[x]=max(maxni[x],i);
maxnj[x]=max(maxnj[x],j);
minni[x]=min(minni[x],i);
minnj[x]=min(minnj[x],j);
}
}
for(int len=1;len<=n;len++){
for(int i=1;i<=n*n;i++){
if(!maxni[i]||!maxnj[i])continue;
ll mxi=max(maxni[i]-len+1,1ll);
ll mxj=max(maxnj[i]-len+1,1ll);
ll mni=min(minni[i],n-len+1);
ll mnj=min(minnj[i],n-len+1);
if(mxi<=mni&&mxj<=mnj){
sum[mxi][mxj]++;
sum[mni+1][mxj]--;
sum[mxi][mnj+1]--;
sum[mni+1][mnj+1]++;
}
}
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
sum[i][j]+=sum[i-1][j]+sum[i][j-1]-sum[i-1][j-1];
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
if(num-sum[i][j]==m||num-sum[i][j]+1==m){
cout<<1;
return 0;
}
}
}
for(int i=1;i<=n;i++)for(int j=1;j<=n;j++)sum[i][j]=0;
}
cout<<2;
return 0;
}