D. Credit Card

Recenlty Luba got a credit card and started to use it. Let's consider n consecutive days Luba uses the card.

She starts with 0 money on her account.

In the evening of i-th day a transaction ai occurs. If ai > 0, then ai bourles are deposited to Luba's account. If ai < 0, then ai bourles are withdrawn. And if ai = 0, then the amount of money on Luba's account is checked.

In the morning of any of n days Luba can go to the bank and deposit any positive integer amount of burles to her account. But there is a limitation: the amount of money on the account can never exceed d.

It can happen that the amount of money goes greater than d by some transaction in the evening. In this case answer will be «-1».

Luba must not exceed this limit, and also she wants that every day her account is checked (the days when ai = 0) the amount of money on her account is non-negative. It takes a lot of time to go to the bank, so Luba wants to know the minimum number of days she needs to deposit some money to her account (if it is possible to meet all the requirements). Help her!

Input
The first line contains two integers n, d (1 ≤ n ≤ 105, 1 ≤ d ≤ 109) —the number of days and the money limitation.

The second line contains n integer numbers a1, a2, ... an ( - 104 ≤ ai ≤ 104), where ai represents the transaction in i-th day.

Output
Print -1 if Luba cannot deposit the money to her account in such a way that the requirements are met. Otherwise print the minimum number of days Luba has to deposit money.

Input

  1. - -

Output

  1.  

Input

  1. -

Output

  1. -

思路:首先由于每次充钱我们只需要保证账户金额不超过d就可以无限充钱,那么我们不会因为检查时金额为负数而输出-1,因为我们一定有能力在检查的那天白天把金额充值到正数。现在的问题是,任何一天的白天金额不能超过d,且希望充值次数最少。所以在每次必须充值的时候,我们尽量多充一些,充多少由后面的前缀最大值定。假设未来的最大前缀是f[j],那么此时最多只能充d - f[j]。(参考博客)

AC代码:

  1. #include<bits/stdc++.h>
  2.  
  3. using namespace std;
  4. #define N 1250000
  5. int arr[N];
  6. int sum[N];// 前缀和
  7. int f[N];//从后面跑出的最大值
  8. int main(){
  9. int n,d;
  10. scanf("%d%d",&n,&d);
  11. for(int i=;i<=n;i++)
  12. scanf("%d",&arr[i]);
  13. sum[]=;
  14. for(int i=;i<=n;i++)
  15. sum[i]=sum[i-]+arr[i];// 前缀和
  16. f[n]=sum[n];
  17. for(int i=n-;i>=;i--)
  18. f[i]=max(f[i+],sum[i]);// 最大值
  19. int ans=;// 需要增加的钱 的数目
  20. int res=;// 需要增加的钱 的金额
  21. for(int i=;i<=n;i++){
  22. if(!arr[i]){
  23. if(sum[i]+res<){ // 给钱的范围 --(不能超过接下来的最大值)
  24. res+=d-(f[i]+res);
  25. ans++;
  26. }
  27. if(res+sum[i]<){ // 如果钱还是为负数。则不符合
  28. puts("-1");
  29. return ;
  30. }
  31. }else{
  32. if(res+sum[i]>d){//
  33. puts("-1");
  34. return ;
  35. }
  36. }
  37. }
  38. printf("%d\n",ans);
  39. return ;
  40. }

 

Educational Codeforces Round 33 (Rated for Div. 2) D题 【贪心:前缀和+后缀最值好题】的更多相关文章

  1. Educational Codeforces Round 33 (Rated for Div. 2) E. Counting Arrays

    题目链接 题意:给你两个数x,yx,yx,y,让你构造一些长为yyy的数列,让这个数列的累乘为xxx,输出方案数. 思路:考虑对xxx进行质因数分解,设某个质因子PiP_iPi​的的幂为kkk,则这个 ...

  2. Educational Codeforces Round 33 (Rated for Div. 2) F. Subtree Minimum Query(主席树合并)

    题意 给定一棵 \(n\) 个点的带点权树,以 \(1\) 为根, \(m\) 次询问,每次询问给出两个值 \(p, k\) ,求以下值: \(p\) 的子树中距离 \(p \le k\) 的所有点权 ...

  3. Educational Codeforces Round 33 (Rated for Div. 2) 题解

    A.每个状态只有一种后续转移,判断每次转移是否都合法即可. #include <iostream> #include <cstdio> using namespace std; ...

  4. Educational Codeforces Round 33 (Rated for Div. 2)A-F

    总的来说这套题还是很不错的,让我对主席树有了更深的了解 A:水题,模拟即可 #include<bits/stdc++.h> #define fi first #define se seco ...

  5. Educational Codeforces Round 33 (Rated for Div. 2) D. Credit Card

    D. Credit Card time limit per test 2 seconds memory limit per test 256 megabytes input standard inpu ...

  6. Educational Codeforces Round 33 (Rated for Div. 2) C. Rumor【并查集+贪心/维护集合最小值】

    C. Rumor time limit per test 2 seconds memory limit per test 256 megabytes input standard input outp ...

  7. Educational Codeforces Round 33 (Rated for Div. 2) B. Beautiful Divisors【进制思维/打表】

    B. Beautiful Divisors time limit per test 2 seconds memory limit per test 256 megabytes input standa ...

  8. Educational Codeforces Round 33 (Rated for Div. 2) A. Chess For Three【模拟/逻辑推理】

    A. Chess For Three time limit per test 1 second memory limit per test 256 megabytes input standard i ...

  9. Educational Codeforces Round 33 (Rated for Div. 2)

    A. Chess For Three time limit per test 1 second memory limit per test 256 megabytes input standard i ...

随机推荐

  1. 【AtCoder】ARC068

    ARC 068 C - X: Yet Another Die Game 显然最多的就是一次6一次5 最后剩下的可能需要多用一次6或者6和5都用上 #include <bits/stdc++.h& ...

  2. Win7原装ISO镜像封装USB3.0&网卡驱动

    Win7原装ISO镜像封装USB3.0&网卡驱动   最新购买的电脑是Windows10系统,想装回Windows7,但是装Windows7发现网络适配器没出现,如果没有USB2.0接口,US ...

  3. MS SQL 2012表分区

    最近开发一个手机用户统计平台,因为涉及到数据庞大,不得不以一周为单位对统计报表进行分区,所以记录一下,方便以后查看 第一步创建文件分组 对于文件分组共创建了14个,从 xy_group_2014102 ...

  4. Thread 和 Runnable

    Thread 和 Runnable 1. 简介 Java 主要是通过 java.lang.Thread 类以及 java.lang.Runnable 接口实现线程机制的. Thread 类为底层操作系 ...

  5. BaseHandler的封装, 处理handler中的内存泄漏

    package de.bvb.study.common; /** * 用于规范 Message.what此属性,避免出现魔法数字 */ public final class What { public ...

  6. AutoFac实现程序集级别的依赖注入

    1.介绍      所谓程序集级别的依赖注入是指接口和实现的依赖不使用配置文件或硬代码实现(builder.RegisterType<UserInfoService>().As<IU ...

  7. c++11 常量表达式

    c++11 常量表达式 #define _CRT_SECURE_NO_WARNINGS #include <iostream> #include <string> #inclu ...

  8. springboot 集成 dubbo(一)简介

    一.简介 1,springboot 是 一款快速开发的框架,减少了开发人员对配置文件的操作.采用一些注解来取代xml配置文件. 注解包含预先封装的注解和开发人员自定义注解.同时使用Maven.Grad ...

  9. docker第三篇 镜像管理基础

    docker 工作原理: 常用的命令docker run .create .start... 都是客户端命令 Docker Daemon 接收到客户端传过来的命令以后 docker daemon会根据 ...

  10. elmentUI为table中的单元格添加事件

    <el-main> <el-tabs v-model="curTab" type="card"> <!-- tab签 --> ...