(CF 792E Colored Balls) 思维题 贪心

14 篇文章 0 订阅
11 篇文章 0 订阅

题目链接http://codeforces.com/problemset/problem/792/E

E. Colored Balls

time limit per test:
1 second

memory limit per test:
256 megabytes

input:
standard input

output:
standard output

There are n boxes with colored balls on the table. Colors are numbered from 1 to n. i-th box contains ai balls, all of which have color i. You have to write a program that will divide all balls into sets such that:
• each ball belongs to exactly one of the sets,
• there are no empty sets,
• there is no set containing two (or more) balls of different colors (each set contains only balls of one color),
• there are no two sets such that the difference between their sizes is greater than 1.

Print the minimum possible number of sets.

Input

The first line contains one integer number n (1 ≤ n ≤ 500).

The second line contains n integer numbers a1, a2, … , an (1 ≤ ai ≤ 10^9).

Output

Print one integer number — the minimum possible number of sets.

Examples

Input
3
4 7 8

Output
5

Input
2
2 7

Output
4

Note

In the first example the balls can be divided into sets like that: one set with 4 balls of the first color, two sets with 3 and 4 balls, respectively, of the second color, and two sets with 4 balls of the third color.

思路:

//
题意:有n个盒子,每个盒子里面有ai个颜色为i的球。问将他们可以分为最少多少堆?每堆满足一下条件
1:所有堆的球数的差值不超过1
2:每堆的颜色一样

分析: 题目的意思就是可以将每一大堆可以最少分为几个小堆来满足条件
由于差值不差过1,所以我们假设n个盒子中球最少的球数为mina个
所以每堆最多的球数x 从mina+1开始考虑,一直到1
当每堆最多的球数为x时,每个盒子只要满足下里面两种情况就满足题目条件: 其中t = ai / x; d = ai % x;
1:d == 0  直接分为t堆
2:d + t >= x - 1  分为t + 1 堆,有的为x,有的为x-1

关于对x的值得处理:
将球数最小的盒子分为1堆 : 有两种情况 x = mina + 1 或 x = mina
将球数最小的盒子分为2堆 : 有两种情况 想= mina/2 + 1 或 x = mina/2
.....依次类推即可

//

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
using namespace std;

const int maxn = 510;
int a[maxn];
int n;
long long ans;

int judge(int x)
{
    ans = 0;
    int i,t,d;
    for(i=1;i<=n;i++)
    {
        t = a[i]/x;
        d = a[i]%x;
        if(d == 0) ans += t;
        else if(d+t >= x-1) ans += t + 1;
        else return 0;
    }
    return 1;
}

int main()
{
    int mina = 1000000010;
    scanf("%d",&n);
    for(int i=1;i<=n;i++)
    {
        scanf("%d",&a[i]);
        if(a[i] < mina) mina = a[i];
    }
    for(int i=1;i<=mina;i++)
    {
        if(judge(mina/i + 1)) break;
        else if(judge(mina/i)) break;
    }
    printf("%I64d\n",ans);
    return 0;
}
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值