hdu 1227 简单dp+中位数的性质
2015-02-05 11:01
281 查看
有一列数X1,X2,X3,...,Xn
f(x)=|X1-x|+|X2-x|+|X3-x|+...+|Xn-x|
当x=数列中位数时,f(x)最小
在做这道题前一定要知道这条结论,然后开始考虑如何进行解题,首先我们定义状态
dp[i][j], i代表现在已经建设了多少个供给站,j代表当前供应到了第几个城市.
那么我们要更新当前情况,必须找到上一个供给站的装态,所以枚举最后一个城市,在i到j之间,然后因为中位数的性质,每次我们建设供给站一定是在中位数的位置.
f(x)=|X1-x|+|X2-x|+|X3-x|+...+|Xn-x|
当x=数列中位数时,f(x)最小
在做这道题前一定要知道这条结论,然后开始考虑如何进行解题,首先我们定义状态
dp[i][j], i代表现在已经建设了多少个供给站,j代表当前供应到了第几个城市.
那么我们要更新当前情况,必须找到上一个供给站的装态,所以枚举最后一个城市,在i到j之间,然后因为中位数的性质,每次我们建设供给站一定是在中位数的位置.
#include <iostream> #include <cstring> #include <algorithm> #include <cstdio> #include <cstdlib> #define MAX 207 using namespace std; int n,m; int dp[MAX][MAX]; int d[MAX]; int c[MAX][MAX]; int main ( ) { int cc = 1; while ( ~scanf ( "%d%d" , &n , &m ) , n+m ) { for ( int i = 1 ; i <= n ; i++ ) scanf ( "%d" , &d[i] ); memset ( c, 0 , sizeof ( c ) ); for ( int i = 1 ; i <= n ; i++ ) for ( int j = i; j <= n ; j++ ) for ( int k = i ; k <= j ; k++ ) c[i][j] += abs ( d[k] - d[(i+j)/2] ); memset ( dp , 0x7f , sizeof ( dp ) ); // cout << dp[0][0] << endl; dp[0][0] = 0; for ( int i = 1 ; i <= n ; i++ ) dp[1][i] = c[1][i]; for ( int i = 2 ; i <= m ; i++ ) for ( int j = i ; j <= n ; j++ ) for ( int k = i-1 ; k < j ; k++ ) dp[i][j] = min ( dp[i][j] , dp[i-1][k] + c[k+1][j] ); printf ( "Chain %d\n" , cc++ ); printf ( "Total distance sum = %d\n" , dp[m] ); puts ( "" ); } }
相关文章推荐
- HDU 1227 Fast Food(简单二维dp)
- HDU 1227 dp距离和最小,中位数的应用
- HDU 2084 数塔 简单DP
- HDU 1160 FatMouse's Speed 最长上升子序列 简单DP
- HDU 3485 Count 101(简单DP)
- hdu 3835 简单概率dp
- HDU 1078 FatMouse and Cheese (简单DP)
- hdu 1087 DP简单题
- hdu_2151 worm ( 简单DP )
- HDU 3016 线段树+简单dp
- HDU 1520 Anniversary party(简单树形DP)
- 【HDU 1058 & HDU 3199 类似丑数】 简单DP思想
- hdu 1693(插头DP简单题,多条回路)
- hdu 1466计算直线的交点数 (简单dp)
- hdu 2391 Filthy Rich (简单dp)
- hdu 2602 Bone Collector 简单dp题 0-1背包
- HDU 1087 Super Jumping! Jumping! Jumping! 简单DP
- hdu1579简单的用dp优化递归
- ZOJ1733 | | HDU1159简单的DP求两个字符串最大子序列的长度,没啥好说的,照着书上敲得。
- hdu 3848 CC on the tree 简单树形dp