Codeforces Gym100342E Minima

来源:互联网 发布:新疆教师网络平台登录 编辑:程序博客网 时间:2024/06/07 10:12

Problem E. Minima

Input file: minima.in
Output file: minima.out
Time limit: 2 seconds
Memory limit: 512 megabytes

You are given an array x[1 … n] and a number m. For all i from 1 to n−m+ 1 find the minimum among x[i], x[i + 1], … ,
x[i + m − 1] and return the sum of those minima.

Input

The first line of the input file contains three integer numbers: n, m and k (1 ≤ n ≤ 30 000 000, 1 ≤ m ≤ n,2 ≤ k ≤ min(n,1000)). The second line of the input file contains three integer numbers: a, b and c(−2^31 ≤ a, b, c ≤ 2^31 − 1). The third line of the input file contains k integer numbers: x[1],x[2], … , x[k](−2^31 ≤ x[i] ≤ 2^31 − 1).The rest of the array is calculated using the following formula: x[i] = f(a · x[i − 2] + b · x[i − 1] + c). Heref(y) returns such number −2^31 ≤ z ≤ 2^31 − 1 that y − z is divisible by 2^32.

Output

Print one integer number — the sum of minima of all subarrays of length m of the given array.

Example

minima.in
10 3 2
1 1 0
0 1
minima.out
33
minima.in
1000000 15 5
283471207 23947205 3
17625384 939393931 1838388 912740247 290470294
minima.out
-1879262596173354

题意

一段长为n的序列,给出前k项,后面n-k项可由题目中的函数推算,求所有长为m的区间的最小值之和

题解

维护一个双向队列即可,直接用优先队列会TLE。AC代码如下

#include <cstdio>#include <algorithm>#include <queue>#include <cstdlib>using namespace std;struct node{    int num;    int id;    bool operator<(const node &R)const    {        return num>R.num;    }};deque<node> Q;int n,m,k;int a,b,c;int f1,f2;int temp;node shit;long long ans=0;int f(int x){    if(x<k-1)    {        scanf("%d",&x);        return x;    }    else if(x==k-1)    {        scanf("%d",&f1);        return f1;    }    else if(x==k)    {        scanf("%d",&f2);        return f2;    }    else    {        int t=a*f1+b*f2+c;        f1=f2;        f2=t;        return t;    }}int main(){    freopen("minima.in","r",stdin);    freopen("minima.out","w",stdout);    scanf("%d%d%d",&n,&m,&k);    scanf("%d%d%d",&a,&b,&c);    int i;    for(i=1;i<m;i++)    {        temp=f(i);        while((!Q.empty())&&Q.back().num>temp)            Q.pop_back();        Q.push_back((node){temp,i});    }    for(;i<=n;i++)    {        temp=f(i);        while((!Q.empty())&&Q.back().num>temp)            Q.pop_back();        Q.push_back((node){temp,i});        while(Q.front().id<i-m+1)            Q.pop_front();        ans+=Q.front().num;    }    printf("%I64d\n",ans);    return 0;}
0 0