C. Cloud Computing (线段树)

Buber is a Berland technology company that specializes in waste of investor‘s money. Recently Buber decided to transfer its infrastructure to a cloud. The company decided to rent CPU cores in the cloud for nn consecutive days, which are numbered from 11 to nn . Buber requires kk CPU cores each day.

The cloud provider offers mm tariff plans, the ii -th tariff plan is characterized by the following parameters:

lili and riri — the ii-th tariff plan is available only on days from lili to riri, inclusiv

cici — the number of cores per day available for rent on the ii-th tariff plan,

pipi — the price of renting one core per day on the ii-th tariff plan.

Buber can arbitrarily share its computing core needs between the tariff plans. Every day Buber can rent an arbitrary number of cores (from 0 to cici ) on each of the available plans. The number of rented cores on a tariff plan can vary arbitrarily from day to day.

Find the minimum amount of money that Buber will pay for its work for nn days from 11 to nn . If on a day the total number of cores for all available tariff plans is strictly less than kk , then this day Buber will have to work on fewer cores (and it rents all the available cores), otherwise Buber rents exactly kk cores this day.

Input

The first line of the input contains three integers nn , kk and mm (1≤n,k≤106,1≤m≤2⋅1051≤n,k≤106,1≤m≤2⋅105 ) — the number of days to analyze, the desired daily number of cores, the number of tariff plans.

The following mm lines contain descriptions of tariff plans, one description per line. Each line contains four integers lili , riri , cici , pipi (1≤li≤ri≤n1≤li≤ri≤n , 1≤ci,pi≤1061≤ci,pi≤106 ), where lili and riri are starting and finishing days of the ii -th tariff plan, cici — number of cores, pipi — price of a single core for daily rent on the ii -th tariff plan.

Output

Print a single integer number — the minimal amount of money that Buber will pay.

Examples

Input

Copy

5 7 31 4 5 31 3 5 22 5 10 1

Output

Copy

44

Input

Copy

7 13 52 3 10 73 5 10 101 2 10 64 5 10 93 4 10 8

Output

Copy

462

Input

Copy

4 100 33 3 2 51 1 3 22 4 4 4

Output

Copy

64




首先贪心的想就是无论如何都要先选便宜的,会想到先排序,

然后给的区间有点区间覆盖的意思,也就是往线段树那边去想了,然后发现对一个区间进行覆盖之后,不好从某一个点里取出最小的k个

所以就尬住了qwq

然后题解是用了扫面线的思想,到了第i天,对当前可用的plan建立线段树,那k去线段树上找前k个,这样思路瞬间就清晰了





 1 #include"bits/stdc++.h"
 2 using namespace std;
 3 #define int long long
 4 #define IO ios::sync_with_stdio(0);
 5 vector<int > add[2000000],del[2000000];
 6
 7 struct pp
 8 {
 9    int size,v;
10 }tr[4000000];
11
12 struct aa
13 {
14     int l,r,c,p;
15     bool operator<(const aa b)const
16     {
17         return c<b.c;
18     }
19 }edge[300000];
20 int n,m,k;
21
22 void upd(int rt,int l,int r,int pos,int c)
23 {
24    if(l==r)
25    {
26        tr[rt].size += c;
27        tr[rt].v += pos*c;
28        return ;
29    }int mid = l+r>>1;
30    if(pos<=mid)upd(rt<<1,l,mid,pos,c); else upd(rt<<1|1,mid+1,r,pos,c);
31
32    tr[rt].size = tr[rt<<1].size + tr[rt<<1|1].size;
33    tr[rt].v = tr[rt<<1].v + tr[rt<<1|1].v;
34
35 }
36
37 int que(int rt,int l,int r,int k)
38 {
39     if(l==r)
40     {
41         return min(tr[rt].size,k)*l;
42     }
43     int mid=l+r>>1;
44     if(k<=tr[rt<<1].size)return que(rt<<1,l,mid,k);
45     else return tr[rt<<1].v + que(rt<<1|1,mid+1,r,k-tr[rt<<1].size);
46 }
47
48 signed main()
49 {
50     IO
51     cin>>n>>k>>m; int maxn=1000;
52    for(int i=1;i<=m;++i)
53    {
54        cin>>edge[i].l>>edge[i].r>>edge[i].c>>edge[i].p;
55        add[edge[i].l].push_back(i);   maxn=max(maxn,edge[i].p);
56        del[edge[i].r].push_back(i);
57    }
58   int ans=0;
59   for (int i=1;i<=n;i++)
60   {
61
62       for(auto j:add[i])upd(1,1,maxn,edge[j].p,edge[j].c);
63
64       ans += que(1,1,maxn,k);
65       for (auto j:del[i])upd(1,1,maxn,edge[j].p,-edge[j].c);
66
67   }
68   cout<<ans;
69
70
71
72 }

原文地址:https://www.cnblogs.com/zhangbuang/p/10726015.html

时间: 2024-10-11 21:04:18

C. Cloud Computing (线段树)的相关文章

【非原创】codeforces 1070C Cloud Computing 【线段树&amp;树状数组】

题目:戳这里 学习博客:戳这里 题意:有很多个活动,每个活动有持续天数,每个活动会在每天提供C个CPU每个CPU价格为P,问需要工作N天,每天需要K个CPU的最少花费. 解题思路:遍历每一天,维护当前天K个cpu的最小花费.具体方法是维护两个线段树(树状数组也可以),维护每一天可以使用的cpu数和价格*cpu数的前缀和.注意数组下标是价格(1e6的数组. (不明白的话可以看代码,代码思路很清晰 附学习博客的代码: 1 #include <iostream> 2 3 #include <a

hdu 4267 A Simple Problem with Integers(树形结构-线段树)

A Simple Problem with Integers Time Limit: 5000/1500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 3708    Accepted Submission(s): 1139 Problem Description Let A1, A2, ... , AN be N elements. You need to deal with

poj 2151 Check the difficulty of problems(线段树+概率)

Check the difficulty of problems Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 4465   Accepted: 1966 Description Organizing a programming contest is not an easy job. To avoid making the problems too difficult, the organizer usually exp

poj 2274 The Race(逆序数+线段树)

The Race Time Limit: 15000MS   Memory Limit: 65536K Total Submissions: 3237   Accepted: 664 Case Time Limit: 3000MS Description During the Annual Interstellar Competition for Tuned Spaceships, N spaceships will be competing. Each spaceship i is tuned

hdu 4288 Coder(树形结构-线段树)

<span style="font-family: 'Times New Roman'; font-size: 12px;">Coder</span> Time Limit: 20000/10000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 3187    Accepted Submission(s): 1258 Problem Descr

[poj2104]可持久化线段树入门题(主席树)

解题关键:离线求区间第k小,主席树的经典裸题: 对主席树的理解:主席树维护的是一段序列中某个数字出现的次数,所以需要预先离散化,最好使用vector的erase和unique函数,很方便:如果求整段序列的第k小,我们会想到离散化二分和线段树的做法, 而主席树只是保存了序列的前缀和,排序之后,对序列的前缀分别做线段树,具有差分的性质,因此可以求任意区间的第k小,如果主席树维护索引,只需要求出某个数字在主席树中的位置,即为sort之后v中的索引:若要求第k大,建树时反向排序即可 1 #include

【BZOJ4942】[Noi2017]整数 线段树+DFS(卡过)

[BZOJ4942][Noi2017]整数 题目描述去uoj 题解:如果只有加法,那么直接暴力即可...(因为1的数量最多nlogn个) 先考虑加法,比较显然的做法就是将A二进制分解成log位,然后依次更新这log位,如果最高位依然有进位,那么找到最高位后面的第一个0,将中间的所有1变成0,那个0变成1.这个显然要用到线段树,但是复杂度是nlog2n的,肯定过不去. 于是我在考场上yy了一下,这log位是连续的,我们每次都要花费log的时间去修改一个岂不是很浪费?我们可以先在线段树上找到这段区间

bzoj1798: [Ahoi2009]Seq 维护序列seq 线段树

题目传送门 这道题就是线段树 先传乘法标记再传加法 #include<cstdio> #include<cstring> #include<algorithm> #define LL long long using namespace std; const int M=400010; LL read(){ LL ans=0,f=1,c=getchar(); while(c<'0'||c>'9'){if(c=='-') f=-1; c=getchar();}

Vijos P1066 弱弱的战壕【多解,线段树,暴力,树状数组】

弱弱的战壕 描述 永恒和mx正在玩一个即时战略游戏,名字嘛~~~~~~恕本人记性不好,忘了-_-b. mx在他的基地附近建立了n个战壕,每个战壕都是一个独立的作战单位,射程可以达到无限(“mx不赢定了?!?”永恒[email protected][email protected]). 但是,战壕有一个弱点,就是只能攻击它的左下方,说白了就是横纵坐标都不大于它的点(mx:“我的战壕为什么这么菜”ToT).这样,永恒就可以从别的地方进攻摧毁战壕,从而消灭mx的部队. 战壕都有一个保护范围,同它的攻击