瞎DP一波。
f[i][j]:表示已到达或跳过前i个点,总共跳了j个点,并且目前在第i个点的最小总代价。
f[i][j]=min{ f[k][j-(i-k-1)] }+dis(k,i),(dis(k,i)表示两点间距离。
时间复杂度O(n^3)本来以为过不了的。。
1 #include<cstdio> 2 #include<iostream> 3 #include<cstring> 4 #include<algorithm> 5 using namespace std; 6 const int maxn=503; 7 int x[maxn],y[maxn],dis[maxn][maxn]; 8 int f[maxn][maxn]; 9 int i,j,k,n,m,kk,ans; 10 11 int ra,fh;char rx; 12 inline int read(){ 13 rx=getchar(),ra=0,fh=1; 14 while((rx<‘0‘||rx>‘9‘)&&rx!=‘-‘)rx=getchar(); 15 if(rx==‘-‘)fh=-1,rx=getchar(); 16 while(rx>=‘0‘&&rx<=‘9‘)ra*=10,ra+=rx-48,rx=getchar();return ra*fh; 17 } 18 inline int abs(int x){return x<0?-x:x;} 19 inline int min(int a,int b){return a<b?a:b;} 20 int main(){ 21 n=read(),kk=read(); 22 for(i=1;i<=n;i++){ 23 x[i]=read(),y[i]=read(); 24 for(j=1;j<i;j++)dis[j][i]=abs(x[i]-x[j])+abs(y[i]-y[j]); 25 } 26 memset(f,60,sizeof(f)); 27 f[1][0]=0; 28 for(i=2;i<=n;i++)for(j=0;j<=kk;j++) 29 for(k=max(i-j-1,1);k<i;k++)f[i][j]=min(f[i][j],f[k][j-(i-k-1)]+dis[k][i]); 30 for(i=1,ans=f[n][0];i<=k;i++)ans=min(ans,f[n][i]); 31 printf("%d\n",ans); 32 }
时间: 2024-10-13 03:16:50