• [acmm week12]二分+dp+单调队列


    1004 抄作业
         
     
    Time Limit: 1sec    Memory Limit:256MB
    Description

    Zfree虽然平时很爱学习,但是他迫于生活所迫(比如设计cpu实验啊),这周数分作业只能抄答案了。

    可是这是他第一次抄作业题目又多,于是他有些不想抄,因为他想玩会游戏再抄,于是他打算用一定的时间去抄作业(当然也可以不用完)。

    而这可能抄不完,所以他会选择跳过几题不抄,为了尽量不被老师发现,他想知道他抄写的两题的题号最大间隔最小是多少?(间隔包括他第一个抄的题目前面的题目数量 和 最后一个题目后面的题目数量)

    Input

    第一行 T,n 表示可以用来抄题目的总时间和题目数量(T,n<10^5)

    第二行 n个数字,第i个数字表示抄写第i题要用的时间数(a[i]<T)

    Output

     一个数字k,表示最多隔k题抄一题可以用T时间抄完题目

    Sample Input 
     
    10 5
    5 3 6 1 3
     
    Sample Output
     
    1

    题意:n个数,选取若干个数,其中两个数之间的间隔最大为k,问k最小是多少。

    题解:

    要最大值最小,二分k,然后dp判断当前的k是否可行。
    设dp[i]表示最大间隔不超过k的前提下,前i道题目中,选了第i道题,所用的最短时间。
    dp[i]=min(dp[j])+time[i], i-k-1<=j < i
    这个方程最坏情况是n^2的,但这种形式的方程我们可以用一个单调队列来优化。对于当前的i,队列q储存的可能的j值,满足其dp值递增,每次先判断对首的元素是否>=i-k-1,不满足则出队;用队首元素更新dp[i];若队尾的元素的dp值大于dp[i]则出队(这些元素此后都一定没有i优,不可能用于更新其他dp值),再把i放到队尾。这样总的复杂度就是O(nlogn)的。

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 
     4 const int N=100010;
     5 int a[N],f[N],g[N];
     6 int t,n;
     7 
     8 void init()
     9 {
    10     scanf("%d%d",&t,&n);
    11     for(int i=1;i<=n;i++) scanf("%d",&a[i]);
    12     a[n+1]=0;
    13 }
    14 
    15 bool check(int k)
    16 {
    17     //f[i]=min(f[j])+a[i];  (i-k-1 <= j <= i-1)
    18     int l=1,r=1;
    19     f[0]=0;g[1]=0;
    20     for(int i=1;i<=n+1;i++)
    21     {
    22         while(l<=r && g[l]<i-k-1) l++;
    23         f[i]=f[g[l]]+a[i];
    24         while(l<=r && f[g[r]]>f[i]) r--;
    25         g[++r]=i;
    26     }
    27     return f[n+1]<=t;
    28 }
    29 
    30 void solve()
    31 {
    32     int l=0,r=n,mid;
    33     while(l<r)
    34     {
    35         mid=(l+r)/2;
    36         if(check(mid)) r=mid;
    37         else l=mid+1;
    38     }
    39     printf("%d
    ",l);
    40 }
    41 
    42 int main()
    43 {
    44     //freopen("a.in","r",stdin);
    45     init();
    46     solve();
    47     return 0;
    48 }
  • 相关阅读:
    Screen Space Soft Shadows
    立体涂鸦的草图渲染
    什么是Civil3D
    Visual Studio 和 .NET Framework
    编程语言的选择
    Civil3D二次开发能做些什么
    Civil3D二次开发Cookbook
    Civil3D跟AutoCAD是什么关系
    C#启示录:尝鲜版
    Thinking In DesignPattern
  • 原文地址:https://www.cnblogs.com/KonjakJuruo/p/10028659.html
Copyright © 2020-2023  润新知