1. 程式人生 > >The 2016 ACM-ICPC Asia China-Final Contest Gym - 101194D Ice Cream Tower

The 2016 ACM-ICPC Asia China-Final Contest Gym - 101194D Ice Cream Tower

bre sort 一個 進行 freopen 方法 main The urn

題意:熊貓先生想用一些冰淇淋球來做k層的冰淇淋,規定對於一個冰淇淋中的每一個冰淇淋球(最頂層除外),都大於等於上一層的冰淇淋球的兩倍大小;現有n個冰淇淋球,問最多能做幾個冰淇淋

思路:剛開始想的貪心,最後發現是不行的。比如對於 1 2 3 4 這種情況,1 後面是2還是3就沒法用程序來進行抉擇了。可以用二分的方法,枚舉所有可能的冰淇淋個數x,然後再進行判斷當前的冰淇淋球能否做成x個冰淇淋

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 typedef long long ll;
 4 const int maxn = 3e5 + 100
; 5 ll ans[maxn], tmp[maxn]; 6 int n, k; 7 8 bool judge(int len) { 9 for(int i = 1; i <= len; i++) 10 tmp[i] = ans[i]; 11 int cur = len+1; 12 for(int i = 1; i < k; i++) { 13 for(int j = 1; j <= len; j++) { 14 bool flag = false; 15 for
(int z = cur; z <= n; z++) { 16 if(ans[z] >= tmp[j]*2) { 17 tmp[j] = ans[z]; 18 cur = z+1; 19 flag = true; 20 break; 21 } 22 } 23 if(!flag) return false; 24 }
25 } 26 return true; 27 } 28 29 int main() { 30 // freopen("in.txt", "r", stdin); 31 int t, kase = 1; 32 scanf("%d", &t); 33 while(t--) { 34 scanf("%d%d", &n, &k); 35 for(int i = 1; i <= n; i++) 36 scanf("%lld", &ans[i]); 37 if(k == 1) { 38 printf("Case #%d: %d\n", kase++, n); 39 continue; 40 } 41 sort(ans+1, ans+1+n); 42 int l = 1, r = n/k+n%k+1; 43 while(l < r) { 44 int mid = (l + r) / 2; 45 if(judge(mid)) 46 l = mid + 1; 47 else r = mid; 48 } 49 printf("Case #%d: %d\n", kase++, l-1); 50 } 51 }

The 2016 ACM-ICPC Asia China-Final Contest Gym - 101194D Ice Cream Tower