ABC 312 C - Invisible Hand

翻译: 

n 个卖家 a[i] >= x 卖出   m 个买家 b[i] <= x 买入   x的最小值  使卖的人 >= 买的人

题目要我们出x的最小值。看到a[i], b[i]的范围是10的9次方。可以使用二分查找出x的值。

二分中一定会存在check的编写问题。接下来,我们处理check()。

bool check(int mid)
{
	int x = 0, y = 0;
	for (int i = 1; i <= n; ++ i)
	{
		if (a[i] <= mid)
			x ++;
	}
	for (int i = 1; i <= m; ++ i)
	{
		if (b[i] >= mid)
			y ++;
	}
	return x >= y;
}

 check中。我们要考虑当x=mid时,有多少买家愿意买,多少卖家愿意卖。

最后把check放入二分的while中。

long long l = 1, r = 1e9 + 10, res;
while (l <= r)
{
	long long mid = (l + r) >> 1;
	if (check(mid)) r = mid - 1, res = mid;
	else l = mid + 1;
}

r=1e9的原因是r的最大值为此,二分查找每次砍半,log(1e9) < 40不会爆时间。

好啦。大体的思路就是这样。上代码:

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 2E5 + 10;
int n, m;
int a[MAXN], b[MAXN];  //a:seller   b:buyer

bool check(int mid)
{
	int x = 0, y = 0;
	for (int i = 1; i <= n; ++ i)
	{
		if (a[i] <= mid)
			x ++;
	}
	for (int i = 1; i <= m; ++ i)
	{
		if (b[i] >= mid)
			y ++;
	}
	return x >= y;
}

int main()
{
	cin >> n >> m;
	for (int i = 1; i <= n; ++ i) cin >> a[i];
	for (int i = 1; i <= m; ++ i) cin >> b[i];
	sort(a + 1, a + n + 1);
	sort(b + 1, b + m + 1);
	
	long long l = 1, r = 1e9 + 10, res;
	while (l <= r)
	{
		long long mid = (l + r) >> 1;
		if (check(mid)) r = mid - 1, res = mid;
		else l = mid + 1;
	}
	cout << res << endl; 
	return 0;
} 

点个赞,支持一下。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值