• 吸收遍历Google Code jam 2013 Round 1B A题


    PS:今天上午,非常郁闷,有很多简单基础的问题搞得我有些迷茫,哎,代码几天不写就忘。目前又不当COO,还是得用心记代码哦!

        

    分类:其他 难度:2

        

     Problem

        Armin is playing Osmos, a physics-based puzzle game developed by Hemisphere Games. In this game, he plays a "mote", moving around and absorbing smaller motes.

        A "mote" in English is a small particle. In this game, it's a thing that absorbs (or is absorbed by) other things! The game in this problem has a similar idea to Osmos, but does not assume you have played the game.

        When Armin's mote absorbs a smaller mote, his mote becomes bigger by the smaller mote's size. Now that it's bigger, it might be able to absorb even more motes. For example: suppose Armin's mote has size 10, and there are other motes of sizes 9, 13 and 19. At the start, Armin's mote can only absorb the mote of size 9. When it absorbs that, it will have size 19. Then it can only absorb the mote of size 13. When it absorbs that, it'll have size 32. Now Armin's mote can absorb the last mote.

        Note that Armin's mote can absorb another mote if and only if the other mote is smaller. If the other mote is the same size as his, his mote can't absorb it.

        You are responsible for the program that creates motes for Armin to absorb. The program has already created some motes, of various sizes, and has created Armin's mote. Unfortunately, given his mote's size and the list of other motes, it's possible that there's no way for Armin's mote to absorb them all.

        You want to fix that. There are two kinds of operations you can perform, in any order, any number of times: you can add a mote of any positive integer size to the game, or you can remove any one of the existing motes. What is the minimum number of times you can perform those operations in order to make it possible for Armin's mote to absorb every other mote?

        For example, suppose Armin's mote is of size 10 and the other motes are of sizes [9, 20, 25, 100]. This game isn't currently solvable, but by adding a mote of size 3 and removing the mote of size 100, you can make it solvable in only 2 operations. The answer here is 2.

        

    Input

        The first line of the input gives the number of test cases, T. T test cases follow. The first line of each test case gives the size of Armin's mote, A, and the number of other motes,N. The second line contains the N sizes of the other motes. All the mote sizes given will be integers.

        

    Output

        For each test case, output one line containing "Case #x: y", where x is the case number (starting from 1) and y is the minimum number of operations needed to make the game solvable.

        

    Limits

        1 ≤ T ≤ 100.

        

    Small dataset

        1 ≤ A ≤ 100.
    1 ≤ all mote sizes ≤ 100.
    1 ≤ N ≤ 10.

        

    Large dataset

        1 ≤ A ≤ 106.
    1 ≤ all mote sizes ≤ 106.
    1 ≤ N ≤ 100.

        

    Sample

        每日一道理
    盈盈月光,我掬一杯最清的;落落余辉,我拥一缕最暖的;灼灼红叶,我拾一片最热的;萋萋芳草,我摘一束最灿的;漫漫人生,我要采撷世间最重的———毅力。

        


    Input 
     

    Output 
     
    4
    2 2
    2 1
    2 4
    2 1 1 6
    10 4
    25 20 9 100
    1 4
    1 1 1 1
    Case #1: 0
    Case #2: 1
    Case #3: 2
    Case #4: 4

        题意分析:给出自己的球初始小大a和球的个数n,以及n个球的小大,自己能吸收比自己小的球,然后小大加增吸收球的小大,每次可做两种操纵:1、删掉一个球,2、加增一个球供自己吸收。求起码经过几回操纵,能吸收有所的球。可知,操纵1一定是从后边开始删,操纵2一定是加以后的a-1。

        先将n个球由小到大排序,然后次依遍历n个球,每次将a值累加球的小大,ret录记停止操纵2的数次,当a值小于于等第i个球的小大时,重复a+=a-1,ret++,直到a大于以后球,则遍历到i时停止的操纵为ret次操纵2加上(n-i)次操纵1(除删残余的点),录记最小的ret+n-i,即为所求。注意界边情况便可。

        优化:

        此种法方复杂度为O(n^2),因为每次加增a值使其大于以后球的复杂度不是O(1),可以通过数学盘算成变O(1),设以后球小大为x,设a累加m次的值大于x,

        即:a+(a-1)*(2^m-1) > x,可得:m = ceil( log2(x+1-a)/(a-1) + 1 ), ceil为上取整。

    #include<cstdio>
    #include<cstring>
    #include<cstdlib>
    #include<cmath>
    using namespace std;
    
    const int N=110;
    int a,n,mote[N];
    
    int cmp(const void*x,const void *y)
    {
    	return *(int*)x-*(int*)y;
    }
    
    int cal(int a,int n)
    {
    	if(a==1) return n;
    	int i,j,ret=0,ans=0;
    	for(i=0;i<n;i++)
    	{
    		if(a<=mote[i])
    		{
    			if(ret==0) ans = n-i;
    			else
    			{
    				if(ret+n-i < ans)
    					ans = ret+n-i;
    			}
    			double tmp = mote[i]+1;
    			double ta = ceil(log((tmp-a)/(a-1.0)+1.0) / log(2.0));
    			ret += ta;
    			a += (a-1)*(pow(2.0,ta)-1);
    		}
    		a+=mote[i];
    		//printf("%d %d %d %d\n",i,a,ret,ans);
    	}
    	if(ret < ans) ans = ret;
    	return ans;
    }
    
    int main()
    {
    	freopen("A-large.in","r",stdin);
    	freopen("A-large.out","w",stdout);
    	
    	int t;
    	scanf("%d",&t);
    	for(int cnt=1;cnt<=t;cnt++)
    	{
    		scanf("%d%d",&a,&n);
    		int i,j;
    		for(i=0;i<n;i++)
    			scanf("%d",&mote[i]);
    		qsort(mote,n,sizeof(int),cmp);
    		//for(i=0;i<n;i++)
    		//	printf("%d\n",mote[i]);
    		printf("Case #%d: %d\n",cnt,cal(a,n));
    	} 
    }

        
     

    文章结束给大家分享下程序员的一些笑话语录: 一位程序员去海边游泳,由于水性不佳,游不回岸了,于是他挥着手臂,大声求.救:“F1,F1!”

  • 相关阅读:
    ssh框架下 写简单的hql语句
    onclick事件 在使用模板填充情况下 向后台传递多值
    调用 sendResponseMsg 遇到的问题
    ERP项目有关时间的修改和查看的显示,去掉时分秒
    ERP中select的填充方法
    最简单的jQuery ajax请求
    ERP中默认申请人和申请部门
    list 按元素的某字段排序方法。作者:黄欣
    C# 对象、文件与二进制串(byte数组)之间的转换【转载】
    .net framework(4.6.2) 迁移 .net core(2.2) 总结
  • 原文地址:https://www.cnblogs.com/jiangu66/p/3063672.html
Copyright © 2020-2023  润新知