codevs1513 皇帝的烦恼
题目大意:给定n个点成环,每个点要求染ai个颜色,要求相邻两点不能有相同颜色,求最少颜色。
思路:二分+dp。fi[i]表示i这个点和1最少相同颜色;gi[i]表示i这个点和1最多颜色,互相更新一下。如果fi[n]==0则可以(中间还要注意如果相邻两个点的和大于x也要返回false)。
orz sunshineorz sunshineorz sunshine
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #define maxm 20005 using namespace std; int ai[maxm]={0},fi[maxm]={0},gi[maxm]={0},n; bool judge(int x){ int i,j; memset(fi,127,sizeof(fi)); memset(gi,0,sizeof(gi)); fi[1]=gi[1]=ai[1]; for (i=2;i<=n;++i){ if (ai[i]+ai[i-1]>x) return false; fi[i]=max(0,ai[i]-((x-ai[1])-(ai[i-1]-gi[i-1]))); gi[i]=min(ai[i],ai[1]-fi[i-1]); }return fi[n]==0; } int main(){ int i,l,r=0,mid;scanf("%d",&n); for (i=1;i<=n;++i){scanf("%d",&ai[i]);r+=ai[i];} l=ai[1]; while(l!=r){ if (judge(mid=(l+r)>>1)) r=mid; else l=mid+1; }printf("%d\n",l); }
时间: 2024-11-25 16:02:06