CF1201C·Maximum Median

初见安~这里是传送门:CF #577 Div2 C Maximum Median

Description

You are given an array aa of nn integers, where nn is odd. You can make the following operation with it:

  • Choose one of the elements of the array (for example aiai) and increase it by 11 (that is, replace it with ai+1ai+1).

You want to make the median of the array the largest possible using at most kk operations.

The median of the odd-sized array is the middle element after the array is sorted in non-decreasing order. For example, the median of the array [1,5,2,3,5][1,5,2,3,5] is 33.

Input

The first line contains two integers nn and kk (1≤n≤2⋅1051≤n≤2⋅105, nn is odd, 1≤k≤1091≤k≤109) — the number of elements in the array and the largest number of operations you can make.

The second line contains nn integers a1,a2,…,ana1,a2,…,an (1≤ai≤1091≤ai≤109).

Output

Print a single integer — the maximum possible median after the operations.

Examples

input

3 2
1 3 5

output

5

input

5 5
1 2 1 1 1

output

3

input

7 7
4 1 2 4 3 4 4

output

5

Note

In the first example, you can increase the second element twice. Than array will be [1,5,5][1,5,5] and it's median is 55.

In the second example, it is optimal to increase the second number and than increase third and fifth. This way the answer is 33.

In the third example, you can make four operations: increase first, fourth, sixth, seventh element. This way the array will be [5,1,2,5,3,5,5][5,1,2,5,3,5,5] and the median will be 55.

Sol

要记得开long long……我记住了……

没开long long的代码被后期加上的数据卡掉了……掉了一千多名……【暴风哭泣】

这个题吧——可以进行k次让任意一个数+1,求最大的中位数。因为是只有+1的操作,所以只存在中位数和它前面的原本比他大数进行交换位置。所以我们只考虑 [{mid}, n] 这个范围内的数就行了。后期就可以用于一种类似于填坑的思路来做。

假设我们处理到了范围  [mid, now]  (now <= n) 。

首先肯定是希望数都尽量大,并且保证我们的中位数一直都是中位。如果是这样的一个样例:

5 8
1 2 3 4 10

3和4,3可以和4齐平,用1次操作变成1,2,4,4,10;剩余操作次数9次;

而后两个4一起看,后一个数是10,但是要齐平就需要12次操作,所以我们就可以在10以内让这两个数尽量大,也就是再用8次操作变成:1,2,8,8,10,最大的中位数就是8了。还剩一次操作是没有意义的。

所以就可以得出结论:

如果可以和下一个数齐平,那就一起填上去;如果不够了,那就一起尽量变大,并停止操作就可以了。

上代码——还是很简单的一个题……就是在计算填坑的消耗的时候可能会爆int需要开longlong……【当然不需要像我这样开的丧心病狂】

#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdio>
#include<cmath>
#define maxn 200005
#define int long long//丧心病狂。
using namespace std;
int read() {
	int x = 0, f = 1, ch = getchar();
	while(!isdigit(ch)) {if(ch == '-') f = -1; ch = getchar();}
	while(isdigit(ch)) x = (x << 1) + (x << 3) + ch - '0', ch = getchar();
	return x * f;
}

int n, m, a[maxn];
signed main() {
	n = read(), m = read();
	for(int i = 1; i <= n; i++) a[i] = read();
	
	sort(a + 1, a + 1 + n);
	int cnt = 1, ans = a[n / 2 + 1], now = n / 2 + 1;//先取中间位置
	while(m) {
		if(now < n && m >= 1ll * cnt * (a[now + 1] - a[now])) {//如果没到最后一个,可以填上去
			m -= 1ll * cnt * (a[now + 1] - a[now]); //填
			cnt++, now++; ans = a[now];//往后走一个
		}
		
		else {ans += m / cnt; break;}//否则就可以结束了。不管是到了最后一个还是不够填了
	}
	
	printf("%lld\n", ans);
	return 0;
}

迎评:)
——End——

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值