Codeforces 797(div3)E. Price Maximization

A batch of n goods (n — an even number) is brought to the store, i-th of which has weight ai. Before selling the goods, they must be packed into packages. After packing, the following will be done:

  • There will be n/2 packages, each package contains exactly two goods;
  • The weight of the package that contains goods with indices i and j (1≤i,j≤n) is ai+aj.

With this, the cost of a package of weight x is always ⌊x/k⌋burles (rounded down), where k — a fixed and given value.

Pack the goods to the packages so that the revenue from their sale is maximized. In other words, make such n/2 pairs of given goods that the sum of the values ⌊xi/k⌋, where xi is the weight of the package number i (1≤i≤n/2), is maximal.

For example, let n=6,k=3, weights of goods a=[3,2,7,1,4,8]. Let's pack them into the following packages.

  • In the first package we will put the third and sixth goods. Its weight will be a3+a6=7+8=15. The cost of the package will be ⌊15/3⌋=5 burles.
  • In the second package put the first and fifth goods, the weight is a1+a5=3+4=7. The cost of the package is ⌊7/3⌋=2 burles.
  • In the third package put the second and fourth goods, the weight is a2+a4=2+1=3. The cost of the package is ⌊3/3⌋=1 burle.

With this packing, the total cost of all packs would be 5+2+1=8 burles.

Input

The first line of the input contains an integer t (1≤t≤10^4) —the number of test cases in the test.

The descriptions of the test cases follow.

The first line of each test case contains two integers n (2≤n≤2⋅10^5) and k (1≤k≤10001). The number n — is even.

The second line of each test case contains exactly n integers a1,a2,…,an(0≤ai≤10^9).

It is guaranteed that the sum of n over all the test cases does not exceed 2⋅10^5.

Output

For each test case, print on a separate line a single number — the maximum possible total cost of all the packages.

____________________________________________________________________________

  • 将会有n/2个包装,每个包装正好包含两件商品;
  • 包含带有索引的商品的包裹的重量ai+aj (1≤i,j≤n);

有了这个,一包重量的成本为⌊x/k⌋(向下舍入),其中k— 一个固定的给定值。

将货物包装到包装中,以便最大化其销售收入。                                                                       

____________________________________________________________________________

input

6
6 3
3 2 7 1 4 8
4 3
2 1 5 6
4 12
0 0 0 0
2 1
1 1
6 10
2 0 0 5 9 4
6 5
5 3 8 6 3 2

 

output

8
4
0
2
1
5
_____________________________________________________________________________

题解:

每个物品的重量是a1,a2,…,an;任取其中一个物品ai,则ai=si*k+ai%k,其中si=ai/k,取aj,则aj=sj*k+aj%k,其中sj=aj/k,则(ai+aj)/k=(si*k+ai%k+sj*k+aj%k)/k=si+sj+(ai%k+aj%k)/k,所以任取两个物品得到价值是ai/k+aj/k+两个物品的余数和/k。所以首先不论物品怎样两两组合,最大销售收入都有a1/k+a2/k+…+an/k,这一部分是固定的,剩下的则是取两个物品的余数和/k,要让这一部分尽可能大,也就是说两个物品的余数和/k被浪费掉的要尽可能小,因为物品的余数范围是0,1,..,k-1,即使是取两个最大的余数k-1相加,得(2*k-2)/k<2,也就是说两个物品的余数和/k最大也就是1,到不了2,所以不应该去选两个大的在一起,而应该是去寻找一个大的和一个小的,这样才能更多得到大于k的数。

关键:

  1. 1.将所有ai/k加起来
  2. 2.ai转换成它对应的余数,给它排序,左右指针,左指针找最小,右指针找最大的,优先满足右指针,相加小于k的,左指针直接右移,因为右指针指向的是目前最大的数,目前都不能满足的话,比它小的数更不可能。
  3. 3.小心整型溢出问题。

代码如下:

#include<iostream>
#include<algorithm>
using namespace std;
#define ll long long int
int a[200000];
int main() {
	int t, n, k, i;
	cin >> t;
	while (t--) {
		cin >> n >> k;
		int  l = 0, r = n - 1;
		ll sum = 0;
		for (i = 0; i < n; i++) {
			cin >> a[i];
			sum += a[i] / k;
			a[i] = a[i] % k;
		}
		sort(a, a + n);
		while (l < r) {
			if (a[l] + a[r] >= k) {
				sum += 1;
				l++;
				r--;
			}
			else {
				l++;
			}
		}
		cout << sum << endl;
	}
	return 0;
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值