zoukankan      html  css  js  c++  java
  • 【BZOJ1915】[Usaco2010 Open]奶牛的跳格子游戏 DP+单调队列

    【BZOJ1915】[Usaco2010 Open]奶牛的跳格子游戏

    Description

    奶牛们正在回味童年,玩一个类似跳格子的游戏,在这个游戏里,奶牛们在草地上画了一行N个格子,(3 <=N <= 250,000),编号为1..N。就像任何一个好游戏一样,这样的跳格子游戏也有奖励!第i个格子标有一个数字V_i(-2,000,000,000 <=V_i <= 2,000,000,000)表示这个格子的钱。奶牛们想看看最后谁能得到最多的钱。规则很简单: * 每个奶牛从0号格子出发。(0号格子在1号之前,那里没钱) * 她向N号格子进行一系列的跳跃(也可以不跳),每次她跳到的格子最多可以和前一 个落脚的格子差K格(1 <= K <= N)(比方说,当前在1号格,K=2, 可以跳到2号和3号格子) *在任何时候,她都可以选择回头往0号格子跳,直到跳到0号格子。另外,除了以上规则之外,回头跳的时候还有两条规则: *不可以跳到之前停留的格子。 *除了0号格子之外,她在回来的时候,停留的格子必须是恰巧过去的时候停留的某个格子的前一格(当然,也可以跳过某些过去时候停留的格子)。简单点说,如果i号格子是回来 停留的格子,i+1号就必须是过去停留的格子,如果i+1号格子是过去停留的格子,i号格子不一定要是回来停留的格子。(如果这里不太清楚的可以去看英文原文)她得到的钱就是所有停留过的格子中的数字的和,请你求出最多奶牛可以得到的钱数。 在样例中,K=2,一行5个格子。 一个合法的序列Bessie可以选择的是0[0], 1[0], 3[2], 2[1], 0[0]。(括号里的数表示钱数) 这样,可以得到的钱数为0+0+2+1+0 = 3。 如果Bessie选择一个序列开头为0, 1, 2, 3, ...,那么她就没办法跳回去了,因为她没办法再跳到一个之前没跳过的格子。序列0[0], 2[1], 4[-3], 5[4], 3[2], 1[0], 0[0]是最大化钱数的序列之一,最后的钱数为(0+1-3+4+2+0 = 4)。

    Input

    * 第1行 1: 两个用空格隔开的整数: N 和 K * 第2到N+1行: 第i+1行有一个整数: V_i

    Output

    * 第一行: 一个单个的整数表示最大的钱数是多少。

    Sample Input

    5 2
    0
    1
    2
    -3
    4

    Sample Output

    4

    OUTPUT DETAILS:

    还有一种可能的最大化钱数的序列是: 0 2 4 5 3 1 0

    题解:用f[i]表示既在去的时候跳到i,又在回来时调到i-1的最大钱数,再维护一个前缀和s[i],记录从1到i所有钱数大于0的格子的钱数和,可以列出方程

    然后用单调队列维护一下就好了

    #include <cstdio>
    #include <iostream>
    #include <cstring>
    using namespace std;
    typedef long long ll;
    int n,m,h,t;
    int q[250010];
    ll f[250010],v[250010],s[250010];
    ll ans;
    int main()
    {
    	scanf("%d%d",&n,&m);
    	int i;
    	for(i=1;i<=n;i++)	scanf("%lld",&v[i]);
    	h=1,t=0;
    	for(i=1;i<=n;i++)
    	{
    		s[i]=s[i-1]+max(0ll,v[i]);
    		while(h<=t&&i-q[h]>m)	h++;
    		f[i]=f[q[h]]+s[i-2]-s[q[h]]+v[i]+v[i-1];
    		while(h<=t&&f[q[t]]-s[q[t]]<f[i-1]-s[i-1])	t--;
    		q[++t]=i-1;
    	}
    	ans=s[m];
    	for(i=1;i<=n;i++)	ans=max(ans,f[i]+s[min(i+m-1,n)]-s[i]);
    	printf("%lld",ans);
    	return 0;
    }
  • 相关阅读:
    QML与C++交互
    etcd集群搭建
    Mac book如何允许第三方未知来源程序安装详细教程(小白篇)
    Windows10下搭建基于VSCODE的RISC-V单片机CH32V103开发环境
    Linux的JAVA开发环境部署
    source 'https://api.nuget.org/v3/index.json': The author primary signature validity period has expired
    element-ui + vue ,ant-design + vue , Angular + ZORRO 实现表格自动横纵向合并单元格,并自动根据单元格数据进行添加样式
    VUE Angular通用动态列表组件-亦可为自动轮播组件-01-根据数据量自动纵向滚动,鼠标划入停止滚动
    VUE Angular通用动态列表组件-亦可为自动轮播组件-02-根据数据量自动横向滚动,鼠标划入停止滚动
    echarts系列-样式调整总结
  • 原文地址:https://www.cnblogs.com/CQzhangyu/p/6412540.html
Copyright © 2011-2022 走看看