PKUACM 2018 A: Wife (C18A) 差分约束/DP

$ ightarrow $ 戳我进PKU原题

Wife

总时间限制: 1000ms 内存限制: 65536kB
 

描述

Asa was very busy. He worked all day long, and went home late.
His wife, Ada, supported him without any complaints. But sometimes Asa can see sadness on Ada's face.
 
Asa soon realized that he made Ada very lonely. He decided to change it.
He made a rule for himself: always accompany Ada for no less than 7 hours in any consecutive 7 days.
In order to better manage time, Asa would accompany Ada for integer hours in a day.
 
But it was that simple. Asa had mountains of things to do.
His every hour to accompany Ada came at a price.
The prices differed from day to day, because Asa was not so busy in some days.
 
Asa knew the prices of an hour accompanying Ada in the following $ N $ days.
Please find the minimum sum of prices if Asa followed his rule in these $ N $ days.
You don't need to consider the days before or after these $ N $ days.
 

输入

The first line is an integer $ T (1 le T le 100) $ , indicating the number of test cases.
For each test case:
 
The first line contains an integer $ N (7 le N le 10,000) $, indicating the number of days.
The second line contains $ N $ non-negative integers,
the $ i $-th integer indicates the price of an hour accompanying Ada in the
These integers are less than $ 100,000 $
 

输出

For each test case, output a line containing an integer, indicating the minimum sum of prices if Asa follows his rule.
 

样例输入

 1
 10
 1 6 3 2 4 5 2 1 2 7

样例输出

 14 

 

提示

Asa can spend $ (3,0,0,2,0,0,2,3,0,0) $ hours in corresponding days to accompany Ada.
The total price is $ 3 imes1+2 imes2+2 imes2+3 imes1=14 $.
 

来源

PKU Campus 2018

 

题目大意

  • 在 $ N $ 天内,第 $ i $ 天每陪妹子 $ 1 $ 小时就要付出 $ c_i $ 的代价(陪了妹子就不能刷题了)

  • 每连续的 $ 7 $ 天里至少陪妹子 $ 7 $ 个小时 (不然妹子就跑了)

  • 求出至少需要付出多少代价,$ N le 10000 $

 

题解

  • 这是一个线性规划问题

  • 设第 $ i $ 天陪 $ x_i $ 小时

  • 目标函数 $ min sum_{i=1}^{N}c_i x_i $

  • 约束条件 $ x_i ge 0 , x_i + x_{i+1} + ...... x_{i+6} ge 7 $

  • 用矩阵形式表示

[X= egin{bmatrix} x_1\x_2\ vdots \x_Nend{bmatrix} , C= egin{bmatrix} c_1\c_2\ vdots \c_Nend{bmatrix} , B=egin{bmatrix} 7\7\ vdots \7end{bmatrix} ,A=egin{bmatrix} 1&1&1&1&1&1&1&0&0& cdots &0\0&1&1&1&1&1&1&1&0& cdots &0\ vdots & vdots & vdots & vdots & vdots & vdots & vdots & vdots & vdots & ddots & vdots \0&0&0&0&0&0&0&0&0& cdots &1end{bmatrix} ]

 

  • 线性规划标准型

  • 目标函数 $ min C^T X$

  • 约束条件 $ X ge 0 , AX ge B $

 

  • 线性规划对偶型

  • 目标函数 $ max Y^T B $ (根据对偶定理,与原目标函数最优解相等)

  • 约束条件 $ Y ge 0 , Y^T A le C^T $

  • 这是一个差分约束系统

  • 设 $ s_i = sum_{j=1}^{i} Y_i $ ,目标 $ max7s_N $

  • 约束条件:

  • $ s_i - s_{i-1} ge 0 $

  • $ s_i - s_0 le c_i (i < 7) , s_i - s_{i-7} le c_i (7 le N-7) , s_N - s_{i-1} le (i > N-7) $

然而我并没有写出来,之后再填坑吧


  • 更快的方法是动态规划

  • 结论:每天要么陪 $ 7 $ 小时,要么不陪

 

  • $ F[i] $ 表示前 $ i $ 天,其中第 $ i $ 天必须陪,满足题目要求的最小代价

  • $ F[0]=0 $

  • $ F[i]=min_{i-7 le j < i} {F[j]} +7c_i $

  • 目标: $ min_{N-6 le i le N} { F[i] } $

代码

#include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
using namespace std;
int t,n,c,f[10005],ans;
int main(){
	scanf("%d",&t);
	while(t--){
		scanf("%d",&n);
		memset(f,0x3f,sizeof(int)*(n+1));
		f[0]=0; ans=1e9+7;
		for(int i=1;i<=n;++i){
			scanf("%d",&c);
			for(int j=max(i-7,0);j<i;++j) 
				f[i]=min(f[i],f[j]+7*c);
		}
		for(int i=max(n-6,0);i<=n;++i) ans=min(ans,f[i]);
		printf("%d
",ans);
	}
	return 0;
}
原文地址:https://www.cnblogs.com/PotremZ/p/PKU_C18A.html