109.天才ACM

题目链接

思路:

本题用到了倍增的思想,题目数据量较大, 不推荐使用cin, cout(会超时)。解题思路为,由左到右枚举左端点,然后找最大的有端点。在寻找有端点的时候就用到了倍增思想。

#include<iostream>
#include<algorithm>
using namespace std;

typedef long long ll;
const int N = 5e5 + 10;
ll a[N], f[N];
int n, m;
ll t;
ll get_s(int l, int r) {
	int t = 0;
	for (int i = l; i < r ; i ++)
		f[++t] = a[i];

	sort(f + 1, f + t + 1);
	ll sum = 0;
	for (int i = 1, j = t; i <= m && i < j; i ++, j --) {
		sum += (f[i] - f[j]) * (f[i] - f[j]);
	}
	return sum;
}
int main() {
	int T;
	cin >> T;
	while (T--) {
		cin >> n >> m >> t;
		for (int i = 1; i <= n; i++)
//			cin >> a[i];
			scanf("%d", &a[i]);
		int res = 0;
		int l = 1, e = 1;

		while (e <= n) {
			int p = 1;
			while (p) {
				if (p + e <= n + 1 && get_s(l, e + p) <= t) {
					e += p;
					p <<= 1;
				} else {
					p >>= 1;
				}
			}
			res ++;
			l = e;
		}
		cout << res << endl;
	}

	return 0;
}

 

posted @ 2022-10-05 17:31  Luli&  阅读(23)  评论(0编辑  收藏  举报