Value【NOIP2016提高A组模拟8.17】
2016-08-17 21:54
459 查看
题目
样例输入:
5
8 2
10 7
5 1
11 8
13 3
样例输出:
27
数据范围:
剖解题目
被虐,不想说了QwQ~~思路
其实是因为在前几天做过一道类似的题目,所以自然而然就往背包dp方面去想,因为考虑到这个w会造成后效性,就试着证明些东西。结果后来的dp打错了QAQ~~详细可见“疯狂的火神”这道题。
解法
40%:暴力。时间复杂度:O(n!).100%:对于一个确定的顺序,他的最优值也是确定的。
假设我们选i,j,k这三件物品,那么我们会获得的价值val1=v[i]+v[j]-w[i]+v[k]-w[i]-w[j]。若我们交换其中两项,如顺序改为i,k,j,我们获得价值是val2=v[i]+v[k]-w[i]+v[j]-w[i]-w[k];我们设val1>val2,则化简后有w[j]< w[k],也就是说我们要先选w小的,排个序就好。
按照w大到小排序,然后就是一个背包dp了。设fi,j表示选择前i个物体中,选择最后j个物体能获得最大价值,转移就很容易了。
fi,j=max(fi−1,j,fi−1,j−1+v[i]−w[i]∗(j−1))
时间复杂度:O(n2).
代码
#include<cstdio> #include<algorithm> #include<cstdlib> #include<cstring> #define fo(i,a,b) for(int i=a;i<=b;i++) using namespace std; const int maxn=5005; int n,f[maxn][maxn]; struct cy{ int v,w; }a[maxn]; bool cmp(cy a,cy b) { return a.w>b.w; } int main() { scanf("%d",&n); fo(i,1,n) scanf("%d%d",&a[i].v,&a[i].w); sort(a+1,a+n+1,cmp); fo(i,1,n){ fo(j,1,i) f[i][j]=max(f[i-1][j],f[i-1][j-1]+a[i].v-a[i].w*(j-1)); } int ans=0; fo(i,1,n) ans=max(f [i],ans); printf("%d",ans); }
相关文章推荐
- 【JZOJ4710】【NOIP2016提高A组模拟8.17】Value
- 【NOIP2016提高A组模拟8.17】(雅礼联考day1)Value
- 【NOIP2016提高A组模拟8.17】Value
- JZOJ.4710【NOIP2016提高A组模拟8.17】Value
- JZOJ 4710 Value【NOIP2016提高A组模拟8.17】
- 【NOIP2016提高A组模拟8.17】Value
- 【JZOJ4711】【NOIP2016提高A组模拟8.17】Binary
- JZOJ 4711. 【NOIP2016提高A组模拟8.17】Binary
- 【NOIP2016提高A组模拟8.17】Binary
- 【NOIP2016提高A组模拟8.17】(雅礼联考day1)Matrix
- Matrix 【NOIP2016提高A组模拟8.17】
- 【NOIP2016提高A组模拟8.17】(雅礼联考day1)Binary
- JZOJ 4711 Binary【NOIP2016提高A组模拟8.17】
- JZOJ.4709【NOIP2016提高A组模拟8.17】Matrix
- 【NOIP2016提高A组模拟8.17】Matrix