传送门:https://codeforces.com/group/X8M1G696VN/contest/528869/problem/C
题面:二十年前,广州的北京路步行街北段出土了自唐代直到民国时期的十一层路面,南段则发掘出宋代至明 清时期共五层的拱北楼建筑基址,佐证了北京路自宋代以来作为商业步行街的悠久历史;同时第一届广 东省大学生程序设计竞赛也在位处广州的中山大学举办。二十年后的今天,北京路步行街已成为广州最 负盛名的景点和购物胜地之一,而广东省大学生程序设计竞赛也迎来了自己的二十岁生日。 图:广州的北京路步行街。 在步行街中,有 n 间商店买卖同一种商品,第 i 间商店一件商品的收购价和出售价均为 ai 元。为了防 止过度交易,步行街有一个规定:您在第 i 间商店最多进行 bi 次交易(一次买或一次卖均计为一次交 易),且每次只能交易一件商品。 您准备通过在步行街中买卖这种商品来赚钱。假如初始时有无限的金钱(也就是说,不会因为钱不够而 买不了一件商品),您最多能在步行街中赚到多少总利润?具体来说,“利润”指的是卖出商品获得的金 钱总额,减去购买商品花费的金钱总额。 Input 有多组测试数据。第一行输入一个整数 T 表示测试数据组数。对于每组测试数据: 第一行输入一个整数 n(1 ≤ n ≤ 105),表示商店的数量。 对于接下来 n 行,第 i 行输入两个整数 ai 和 bi(1 ≤ ai , bi ≤ 106),分别表示第 i 间商店的商品价格, 以及该商店可以交易的最大次数。 保证所有数据 n 之和不超过 106。 Output 每组数据输出一行一个整数,表示在步行街中赚到的最大总利润。
Input:2 4 10 2 30 7 20 4 50 1 2 1 100 1 1000
output:100 0
Input | output |
2 | 100 |
4 10 2 30 7 20 4 50 1 | |
2 1 100 1 1000 | 0 |
#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 1e5+10;
signed main()
{
std::ios::sync_with_stdio(false);
std::cin.tie(0);
int t;
cin >> t;
while (t--)
{
int n;
cin >> n;
vector<pair<int, int>> a(n);
for (int i = 0; i < n; i++)
{
cin >> a[i].first >> a[i].second;
}
sort(a.begin(), a.end());
int ans = 0;
int x = 0, y = n - 1;
while (x < y)
{
int sum = min(a[x].second, a[y].second);
ans += sum * (a[y].first - a[x].first);
a[x].second -= sum;
a[y].second -= sum;
if (a[x].second == 0) x++;
if (a[y].second == 0) y--;
}
cout << ans << endl;
}
return 0;
}