您的位置:首页 > 其它

Problem D. Ice Cream Tower (The 2016 ACM-ICPC Asia China-Final Contest)(二分)

2017-08-22 19:47 471 查看
Input file: Standard Input

Output file: Standard Ouptut

Time limit: 6 seconds

Mr. Panda likes ice cream very much especially the ice cream tower. An ice cream tower consists

of K ice cream balls stacking up as a tower. In order to make the tower stable, the lower ice cream

ball should be at least twice as large as the ball right above it. In other words, if the sizes of the

ice cream balls from top to bottom are A0, A1, A2, · · · , AK−1, then A0 × 2 ≤ A1, A1 × 2 ≤ A2,

etc.

One day Mr. Panda was walking along the street and found a shop selling ice cream balls. There

are N ice cream balls on sell and the sizes are B0, B1, B2, · · · , BN−1. Mr. Panda was wondering

the maximal number of ice cream towers could be made by these balls.

Input

The first line of the input gives the number of test cases, T. T test cases follow. Each test

case starts with a line consisting of 2 integers, N the number of ice cream balls in shop and K

the number of balls needed to form an ice cream tower. The next line consists of N integers

representing the size of ice cream balls in shop.

Output

For each test case, output one line containing “Case #x: y”, where x is the test case number

(starting from 1) and y is the maximal number of ice cream towers could be made.

Limits

• 1 ≤ T ≤ 100.

• 1 ≤ N ≤ 3 × 10^5

.

• 1 ≤ K ≤ 64.

• 1 ≤ Bi ≤ 10^18

Sample Input

3

4 2

1 2 3 4

6 3

1 1 2 2 4 4

6 3

1 1 2 2 3 4

Sample Output

Case #1: 2

Case #2: 2

Case #3: 1

大致题意:给你n个冰淇淋球,告诉你每个冰淇淋球的体积,你可以将若干个冰淇淋球堆成一个塔,需要满足的条件是当前冰淇淋球的体积至少是在它上面的那个球的体积的两倍,一个塔至少有k层,即一个塔至少由k个冰淇淋组成,问最多可以堆成多少个塔。

思路:显然,塔的数量具有单调性,所以我们可以对答案进行二分。check也十分简单。假设当前能堆成x座塔,那么每个塔的第一个球的体积肯定是越小越好,所以我们先将球的体积进行排序,然后按顺序放置在x座塔上,铺下一层的时候,依旧按顺序来放,只不过需要比较体积是否是上一层的两倍,不是的话接着按顺序选下一个球比较。最后看是否能达到k层。

代码如下

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <map>
#define ll long long

using namespace std;
ll H[300005];
int N,K;
ll cheng[300005];

int solve(int num)
{
int f=1;
for(int i=1;i<=num;i++)
cheng[i]=H[f++];

f--;
int x=1;
if(x==K)
return 1;

while(1)
{
for(int i=1;i<=num;i++)
{
if(f+1>N)
return 0;

else
f++;
while(1)
{
if(H[f]>=cheng[i]*2)
{
cheng[i]=H[f];
break;
}
if(f+1>N)
return 0;
else
f++;
}
}
x++;
if(x==K)
return 1;
}
}
int main()
{
int T;
scanf("%d",&T);
for(int Cas=1;Cas<=T;Cas++)
{
scanf("%d%d",&N,&K);

for(int i=1;i<=N;i++)
scanf("%lld",&H[i]);

sort(H+1,H+N+1);

int l=0,r=N/K+1;
while(r-l>1)
{
int mid=(l+r)/2;
if(solve(mid))
{
l=mid;
}
else
r=mid;
}
printf("Case #%d: %d\n",Cas,l);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐