Title Link
Luogu P1514 water diversion into the city
Solutions:
Search and interval merging are studied synthetically.
The difficulty lies in recording the left and right endpoints of the last row interval. When searching from the first row, pay attention to optimization. It is not that every column in the first row starts searching as the starting point, but the columns larger than the left and right endpoints start searching, which can save time.
Pay attention to sorting in interval merging.
include <iostream> #include<cstdio> #include<cstring> #include<algorithm> using namespace std; const int maxv=233233233; int map[510][510],vis[510][510]; int flag[510]; int g[][2]={-1,0,1,0,0,1,0,-1};//Four directions forward int n,m; struct qujian{//Section int l,r; }c[510]; bool cmp(qujian A,qujian B){//Interval merge, ascending first if(A.l==B.l) return A.r<B.r; return A.l<B.l; } void dfs(int x,int y,int index){//Coordinates x, y, and the point index at the beginning of the first line search if(x==n){ c[index].l=min(c[index].l,y);//Interval labeling c[index].r=max(c[index].r,y); flag[y]=1; } for(int i=0;i<4;i++){ int nx=x+g[i][0]; int ny=y+g[i][1]; if(nx<1||nx>n||ny<1||ny>m) continue; if(!vis[nx][ny]&&map[x][y]>map[nx][ny]){ vis[nx][ny]=1; dfs(nx,ny,index); } } } //int test(){ // for(int i=1;i<=m;i++){ // if(!vis[n][i]) return 1; / / not finished // } // return 0; //} int main(int argc, char** argv) { scanf("%d%d",&n,&m); for(int i=1;i<=n;i++){ for(int j=1;j<=m;j++){ scanf("%d",&map[i][j]); if(i==1) c[j].l=maxv; } } for(int i=1;i<=m;i++){ if(map[1][i]>=map[1][i-1]&&map[1][i]>=map[1][i+1]){//Optimize 1, start from the first line to select the points that meet the conditions and search down memset(vis,0,sizeof(vis)); dfs(1,i,i); } } int cnt=0; for(int j=1;j<=m;j++){ if(!flag[j]) cnt++;//If flag[j]==0, the last row, column j, is not accessed. } if(cnt==0){ sort(c+1,c+m+1,cmp);//Ascending order int len=m; while(c[m].l==maxv) --m;//Remove previously inaccessible values // for(int i=1;i<=m;i++) // printf("%d %d\n",c[i].l,c[i].r); //Interval merging after sorting int i1=1,tr=1,ans=0;//Left end, right end of interval, cumulative value ans while(tr<=len){ int temp=0; while(c[i1].l<=tr){ temp=max(temp,c[i1].r); i1++; } tr=temp+1; ans+=1; } printf("1\n%d\n",ans); } else{ printf("0\n%d\n",cnt); } return 0; }