1694: [Usaco2007 Demo]Grazing on the Run
Time Limit: 5 Sec
Memory Limit: 64 MB
Submit: 147
Solved: 94
[ Submit][ Status][ Discuss]
Description
A long, linear field has N (1 <= N <= 1,000) clumps of grass at unique integer locations on what will be treated as a number line. Think of the clumps as points on the number line. Bessie starts at some specified integer location L on the number line (1 <= L <= 1,000,000) and traverses the number line in the two possible directions (sometimes reversing her direction) in order to reach and eat all the clumps. She moves at a constant speed (one unit of distance in one unit of time), and eats a clump instantly when she encounters it. Clumps that aren't eaten for a while get stale. We say the ``staleness'' of a clump is the amount of time that elapses from when Bessie starts moving until she eats a clump. Bessie wants to minimize the total staleness of all the clumps she eats. Find the minimum total staleness that Bessie can achieve while eating all the clumps.
Input
* Line 1 : Two space-separated integers: N and L. * Lines 2..N+1: Each line contains a single integer giving the position P of a clump (1 <= P <= 1,000,000).
Output
* Line 1: A single integer: the minimum total staleness Bessie can achieve while eating all the clumps.
Sample Input
4 10
1
9
11
19
INPUT DETAILS:
Four clumps: at 1, 9, 11, and 19. Bessie starts at location 10.
Sample Output
44
OUTPUT DETAILS:
Bessie can follow this route:
* start at position 10 at time 0
* move to position 9, arriving at time 1
* move to position 11, arriving at time 3
* move to position 19, arriving at time 11
* move to position 1, arriving at time 29
giving her a total staleness of 1+3+11+29 = 44. There are other routes
with the same total staleness, but no route with a smaller one.
显然牛每次吃完一棵草都是在某个区间的左/右端点。。因为把路过的草吃掉总比不吃来得好
那么这题就变成一道区间dp,设f[i][j][k]为区间[i,j]在k(左,右)端点的最小值
然后。。。没啦!
所以区间dp是建立在比它更小的区间上完成的~
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#include<string>
#include<queue>
#include<stack>
#include<vector>
#include<cstdlib>
#include<map>
#include<cmath>
using namespace std;
const int maxn = 1e3 + 10;
typedef long long LL;
LL f[maxn][maxn][2],a[maxn],n,i,j,s;
int main()
{
#ifndef ONLINE_JUDGE
#ifndef YZY
freopen(".in","r",stdin);
freopen(".out","w",stdout);
#else
freopen("yzy.txt","r",stdin);
#endif
#endif
cin >> n >> s;
for (i = 1; i <= n; i++) scanf("%d",&a[i]);
sort (a + 1,a + n + 1);
memset(f,127,sizeof(f));
for (i = 1; i <= n; i++) f[i][i][0] = f[i][i][1] = abs(a[i] - s) * n;
for (int l = 2; l <= n; l++)
for (i = 1; i <= n - l + 1; i++)
{
j = i + l - 1;
f[i][j][0] = min(f[i][j][0],f[i+1][j][0] + abs(a[i+1] - a[i]) * (n-l+1));
f[i][j][0] = min(f[i][j][0],f[i+1][j][1] + abs(a[j] - a[i]) * (n-l+1));
f[i][j][1] = min(f[i][j][1],f[i][j-1][0] + abs(a[i] - a[j]) * (n-l+1));
f[i][j][1] = min(f[i][j][1],f[i][j-1][1] + abs(a[j] - a[j-1]) * (n-l+1));
}
cout << min(f[1][n][0],f[1][n][1]);
return 0;
}