Alice’s Print Service
Description
Alice is providing print service, while the pricing doesn’t seem to be reasonable, so people using her print service found some tricks to save money.
For example, the price when printing less than 100 pages is 20 cents per page, but when printing not less than 100 pages, you just need to pay only 10 cents per page. It’s easy to figure out that if you want to print 99 pages, the best choice is to print an extra blank page so that the money you need to pay is 100 × 10 cents instead of 99 × 20 cents.
Now given the description of pricing strategy and some queries, your task is to figure out the best ways to complete those queries in order to save money.
Input
The first line contains an integer T (≈ 10) which is the number of test cases. Then T cases follow.
Each case contains 3 lines. The first line contains two integers n, m (0 < n, m ≤ 10 5 ). The second line contains 2n integers s 1, p 1 , s 2, p 2 , …, s n, p n (0=s 1 < s 2 < … < s n ≤ 10 9 , 10 9 ≥ p 1 ≥ p 2 ≥ … ≥ p n ≥ 0).. The price when printing no less than s i but less than s i+1 pages is p i cents per page (for i=1..n-1). The price when printing no less than s n pages is p n cents per page. The third line containing m integers q 1 .. q m (0 ≤ q i ≤ 10 9 ) are the queries.
Output
For each query q i, you should output the minimum amount of money (in cents) to pay if you want to print q i pages, one output in one line.
Sample Input
1
2 3
0 20 100 10
0 99 100
Sample Output
0
1000
1000
题意:打印东西,然后打印的页数在不同区间价格不一样,现有两个数组,s[n]和p[n]数组,其意义是在区间s[i]~s[i+1]表示中每页纸的价格是p[i],其中(0=s 1 < s 2 < … < s n ≤ 10 9 , 10 9 ≥ p 1 ≥ p 2 ≥ … ≥ p n ≥ 0)现给一个打印的页数,求需要的最少钱数。
分析:最少的钱数有可能在两个值之间取,第一个就是要打印的页数page按每页的价格打印,第二个就是多打印一些空白页,凑够下一个区间的范围,用下一区间的价格打印。比如所给样例,当打印99张时,如果按照当前区间价格打印就需要99*20,而如果多打印1张空白纸,所需的钱就是100*10。所以,我们可以定义一个数组minx【n】来表示在第i个区间以后打印页数的最小值,然后每次只需求min(minx[i],page*p[i])
比如输入 0,20,200,20000,1000,1
当页数为20的时候,你会发现直接打印最省钱为400
而页数为190时候,直接打印到1000最省钱为1000
代码:
#include<iostream>
#include<string>
#include<cstdio>
#include<cstring>
#include<vector>
#include<math.h>
#include<map>
#include<queue>
#include<algorithm>
using namespace std;
const int inf = 0x3f3f3f3f;
int n,m;
long long s[100005];//页数的区间
long long p[100005];//在区间之间的价格
long long minx[100005];//存放在第i个区间后面的最小花费
int main ()
{
int t;
scanf ("%d",&t);
while (t--){
scanf ("%d%d",&n,&m);
for (int i=0;i<n;i++){
scanf ("%lld%lld",&s[i],&p[i]);
}
minx[n-1]=p[n-1]*s[n-1];
long long tmp=minx[n-1];
for (int i=n-2;i>0;i--){//求minx数组
if (s[i]*p[i]<tmp){
tmp=s[i]*p[i];
minx[i]=tmp;
}
else minx[i]=tmp;
}
minx[0]=tmp;
int page;
for (int i=0;i<m;i++){
scanf ("%d",&page);
if (page==0) {//如果为0直接输出
printf ("0\n");
continue;
}
if (page>=s[n-1]){//当页数大于最后一个区间的起始页数,直接输出
printf ("%lld\n",page*p[n-1]);
continue;
}
int place=upper_bound (s,s+n,page)-s;//求页数的区间
if (page*p[place-1]<minx[place]){//比较那个小
printf ("%lld\n",page*p[place-1]);
}
else {
printf ("%lld\n",minx[place]);
}
}
}
return 0;
}