Hatena::Grouptopcoder

tsubosakaの日記

2009-03-08

TCO 09 Round 1 Medium

| 04:05

ネットで順序統計量とか調べると公式が載っているのでそれを実装しただけです。

public class KthProbableElement {
  double fact(int n){
    double res = 1.0;
    for(int i = 1 ; i <= n ; i++)
      res *= i;
    return res;
  }
  public double probability(int M, int lowerBound, int upperBound, int N, int K) {
    double res = 0.0;
    double pi = 1.0 * (N - lowerBound + 1) / (upperBound - lowerBound + 1);
    double pii = 1.0 * (N - lowerBound ) / (upperBound - lowerBound + 1);
    for(int k = K ; k <= M ; k++){
      double cmb = fact(M) / (fact(k) * fact(M - k)); 
      double r = Math.pow(pi , k) * Math.pow(1.0 - pi ,M - k);
      r -= Math.pow(pii , k) * Math.pow(1.0 - pii ,M - k);
      res += r * cmb;
    }
    return res;
  }
}

TCO 09 Round 1 Easy

| 04:01

数列の長さlを固定すると、数列の和は初項をaとしたときに(l * a + (l-1) * l / 2)となる.この値を=Nとおいたときにaが正の整数解となればよい。後はlをLから100まで動かしていけばよい。

  public int[] sequence(int N, int L) {
    for(int len = L ; len <= 100 ; len++){
      int s = (len - 1) * len / 2;
      int d = N - s;
      if(d >= 0){
        if(d % len == 0){
          int a = d / len;
          int res[] = new int[len];
          res[0] = a;
          for(int i = 1 ; i < res.length ; i++)
            res[i] = res[i - 1] + 1;
          return res;
        }        
      }
    }
    return new int[0];
  }

2009-02-25

TCO 09 Qualification Round 1 Medium

| 00:19

1 <= min <= 10^12, min <= max <= min + 10^6のときに自乗数(4,9,16...)で割り切れない数が[min,max]にいくつあるか答えよという問題.

素因数の候補としてはsqrt(min) <= 10^6までの数の自乗した値に関して調べればよい。調べ方としては[min,max]の中で自乗数を素因数としてもつ最小の値から素因数おきにふるっていけばよい。

import java.util.*;

public class SquareFreeNumbers {
  public int getCount(long min, long max) {
    int N =(int)(max - min + 1);
    boolean memo[] = new boolean[N];
    Arrays.fill(memo, true);
    for(long p = 2 ; p * p <= max ; p++){
      long p2 = p * p;
      long s = ((min + p2 - 1)/ p2) * p2;
      for(; s <= max ; s += p2)
        memo[(int)(s - min)] = false;      
    }
    int res = 0;
    for(int i = 0 ; i < memo.length ; i++)
      if(memo[i])res++;    
    return res;
  }
}

TCO 09 Qualification Round 1 Easy

| 00:10

各数に関して自分より大きいものが何個あるかを数えるだけ。同じ場合は前にあるもののみを数える


public class SortingWithPermutation {
  public int[] getPermutation(int[] a) {
    int N = a.length;
    int[] res = new int[N];
    for(int i = 0 ; i < N ; i++){
      int cnt = 0;
      for(int j = 0 ; j < N ; j++)
        if((a[i] > a[j]) ||
           (a[i] == a[j] && i > j))
          cnt++;      
      res[i] = cnt;
    }
    return res;
  }
}

TCO 09 Qualification Round 1

| 00:07

全完.

250はN^2だと簡単に書ける.

500はmax < 2^40より高々2から2^20までの自乗に関して割り切れるかを調べればよい

1000は二部マッチング