• topcoder srm 390 div1


    problem1 link

    记录一个模$k$之后的值是否出现过,出现过则出现循环,无解;否则最多$k$ 次一定能出现0.

    import java.util.*;
    import java.math.*;
    import static java.lang.Math.*;
    
    public class ConcatenateNumber {
    	
    	public int getSmallest(int number, int k) {
    		if(k==1) {
    			return 1;
    		}
    		boolean[] f=new boolean[k];
    		final long b=getbase(number);
    		int cur=0;
    		for(int i=1;;++i) {
    			cur=(int)((cur*b+number)%k);
    			if(cur==0) {
    				return i;
    			}
    			if(f[cur]) {
    				return -1;
    			}
    			f[cur]=true;
    		}
    	}
    
    	long getbase(int x) {
    		long result=1;
    		while(x>0) {
    			result*=10;
    			x/=10;
    		}
    		return result;
    	}
    }
    

      

    problem2 link

    最朴素的方法应该是令$f[i][mask]$表示处理前$i$块板子使用的painter的集合是$mask$的最小值,但是这样会超时。

    时间上可以接受的方法是二分。首先列举所有可能的时间,然后对时间进行二分。二分之后,令$p[i][j]$表示第$i$个painter从第$j$个board开始能涂到的板子的编号。然后进行动态规划。令$dp[mask]$表示$mask$集合的painter可以涂到的板子的最大编号。

    import java.util.*;
    import java.math.*;
    import static java.lang.Math.*;
    
    public class PaintingBoards {
    
    
    
    	public double minimalTime(int[] boardLength, int[] painterSpeed) {
    		final int n=boardLength.length;
    		final int m=painterSpeed.length;
    		List<Double> list=new ArrayList<>();
    		for(int i=0;i<n;++i) {
    			double cur=0;
    			for(int j=i;j<n;++j) {
    				cur+=boardLength[j];
    				for(int k=0;k<m;++k) {
    					list.add(cur/painterSpeed[k]);
    				}
    			}
    		}
    		Collections.sort(list);
    		int low=0,high=list.size()-1;
    		int result=high;
    		while(low<=high) {
    			int mid=(low+high)>>1;
    			if(check(list.get(mid),boardLength,painterSpeed)) {
    				result=Math.min(result,mid);
    				high=mid-1;
    			}
    			else {
    				low=mid+1;
    			}
    		}
    		return list.get(result);
    	}
    
    	boolean check(double mid,int[] board,int[] painter) {
    		final int n=board.length;
    		final int m=painter.length;
    		int[][] p=new int[m][n];
    		for(int i=0;i<m;++i) {
    			final double s=mid*painter[i]+1e-10;
    			for(int j=0;j<n;++j){
    				double x=0;
    				int y=j;
    				while(y<n&&x+board[y]<=s) {
    					x+=board[y++];
    				}
    				p[i][j]=y;
    			}
    		}
    		int[] f=new int[1<<m];
    		for(int i=1;i<(1<<m);++i) {
    			for(int j=0;j<m;++j) {
    				if((i&(1<<j))!=0) {
    					if(f[i^(1<<j)]==n) {
    						f[i]=n;
    						break;
    					}
    					f[i]=Math.max(f[i],p[j][f[i^(1<<j)]]);
    				}
    			}
    		}
    		return f[(1<<m)-1]==n;
    	}
    
    }
    

      

    problem3 link

    分两步:

    第一步,计算使用$i$个可以拼成的集合$all[i]$,$1 leq i leq 10$;

    第二步,从$frac{a}{b}$开始进行逆向搜索,令集合$unall[i]$中的每个元素$x$表示$x$可以和某个$all[i]$中的元素$y$可以组装成$frac{a}{b}$。

    import com.sun.imageio.spi.RAFImageInputStreamSpi;
    
    import java.util.*;
    import java.math.*;
    import static java.lang.Math.*;
    
    public class BuildCircuit {
    
    
    	static long gcd(long x,long y) {
    		return y==0?x:gcd(y,x%y);
    	}
    
    	static class Rational {
    		public long p;
    		public long q;
    
    		public Rational() {}
    		public Rational(long x,long y) {
    			long t=gcd(x,y);
    			this.p=x/t;
    			this.q=y/t;
    		}
    
    		public static Rational parallel(Rational r1,Rational r2) {
    			return new Rational(r1.p*r2.p, r1.p*r2.q+r1.q*r2.p);
    		}
    
    		public static Rational unparallel(Rational r1,Rational r2)
    		{
    			long t=r1.q*r2.p-r1.p*r2.q;
    			if(t<=0) {
    				return null;
    			}
    			return new Rational(r1.p*r2.p,t);
    		}
    
    		public static Rational serial(Rational r1,Rational r2)
    		{
    			return new Rational(r1.p*r2.q+r1.q*r2.p,r1.q*r2.q);
    		}
    
    		public static Rational unserial(Rational r1,Rational r2)
    		{
    			long t=r1.p*r2.q-r1.q*r2.p;
    			if(t<=0){
    				return null;
    			}
    			return new Rational(t,r1.q*r2.q);
    		}
    
    
    		public boolean equals(Object object) {
    			Rational t=(Rational)object;
    			return p==t.p&&q==t.q;
    		}
    		public int hashCode() {
    			return (int)((p*1007+q)%1000000007);
    		}
    	}
    
    	
    	public int minimalCount(int a,int b) {
    		List<List<Rational>> all=new ArrayList<>();
    		for(int i=0;i<11;++i) {
    			all.add(new ArrayList<>());
    		}
    		Rational one=new Rational(1,1);
    		Rational two=new Rational(2,1);
    		all.get(1).add(one);
    		all.get(1).add(two);
    		Map<Rational,Integer> map1=new HashMap<>();
    		map1.put(one,1);
    		map1.put(two,1);
    
    		for(int i=2;i<=10;++i) {
    			for(int x=1;x<=i-x;++x) {
    				final int y=i-x;
    				for(Rational xx:all.get(x)) {
    					for(Rational yy:all.get(y)) {
    						mark(map1,Rational.parallel(xx,yy),i,all.get(i));
    						mark(map1,Rational.serial(xx,yy),i,all.get(i));
    					}
    				}
    			}
    		}
    
    		List<List<Rational>> unall=new ArrayList<>();
    		for(int i=0;i<11;++i) {
    			unall.add(new ArrayList<>());
    		}
    		Rational need=new Rational(a,b);
    		unall.get(0).add(need);
    		Map<Rational,Integer> map2=new HashMap<>();
    		map2.put(need,0);
    		for(int i=1;i<=10;++i) {
    			for(int x=0;x<i;++x) {
    				final int y=i-x;
    				for(Rational xx:unall.get(x)) {
    					for(Rational yy:all.get(y)) {
    						mark(map2,Rational.unparallel(xx,yy),i,unall.get(i));
    						mark(map2,Rational.unserial(xx,yy),i,unall.get(i));
    					}
    				}
    			}
    		}
    
    		int result=17;
    		for(int i=0;i<=10;++i) {
    			for(Rational x:unall.get(i)) {
    				if(map1.containsKey(x)) {
    					result=Math.min(result,i+map1.get(x));
    				}
    			}
    		}
    		if(result==17) {
    			return -1;
    		}
    		return result;
    
    	}
    
    	void mark(Map<Rational,Integer> map,Rational object,int num,
    			  List<Rational> list) {
    		if(object==null) {
    			return;
    		}
    		if(map.containsKey(object)) {
    			return;
    		}
    		map.put(object,num);
    		list.add(object);
    	}
    }
    

      

  • 相关阅读:
    【SQL Server】数据库是单个用户的 无法顺利进行操作 怎么解决
    【java 断点续传】
    【SQL 触发器】
    【SQL 数据库】将一张数据表信息复制到另一张数据表
    【java 获取数据库信息】获取MySQL或其他数据库的详细信息
    【zTree】 zTree使用的 小例子
    【前台 ajax】web项目前台传递数组给后台 两种方式
    【POI xls Java map】使用POI处理xls 抽取出异常信息 --java1.8Group by ---map迭代 -- 设置单元格高度
    Linux 在VMware中搭建CentOS6.5虚拟机
    HTML5 Canvas实现360度全景图
  • 原文地址:https://www.cnblogs.com/jianglangcaijin/p/7537909.html
Copyright © 2020-2023  润新知