読者です 読者をやめる 読者になる 読者になる

ゆとりーなの日記

日記的な事を書いて行くと思はれる

言語別コンテスト

少し前のとある課題の速度勝負というイベントが発生したのでいざ勝負したわけです。

エントリーNo.1 D言語

import std.stdio;
import std.algorithm;
import std.random;

Random gen;
int[] result = [0, 1, 2, 2, 1, 0, 1, 1, 1, 0, 0, 0, 2, 1];
 
int count() { 
  for (int i = 0; ; ++i) {
    int j;
    for (j = 0; j < 14; ++j) {
      if (result[j] != uniform(0, 3, gen)) {
        break;
      }
    }
    if (j == 14) {
      return i;
    }
  }
}
 
void main() {
  int[2000] counts;
  gen.seed(unpredictableSeed);
  for (int i = 0; i < counts.length; ++i) {
    counts[i] = count();
    writef("%04d %d\n", i, counts[i]);
  }
  auto sum = reduce!("a + b")(0.0, counts);
  auto avr = sum / counts.length;
  writeln(avr);
}

コンパイル

dmd -O -release -inline

結果

平均 4822340回
実行時間 9分34.293秒

エントリーNo.2 Java

import java.util.Random;

public class Dai3No1 {
  private static int[] result = {0, 1, 2, 2, 1, 0, 1, 1, 1, 0, 0, 0, 2, 1};
  static Random r = new Random();
	
  private static int count() {
    for (int i = 0; ; ++i) {
      int j;
      for (j = 0; j < 14; ++j) {
        if (result[j] != r.nextInt(3)) {
          break;
        }
      }
      if (j == 14) {
        return i;
      }
    }
  }
	
  public static void main(String[] args) {
    int[] counts = new int[2000];
    for (int i = 0; i < counts.length; ++i) {
      counts[i] = count();
      System.out.printf("%04d %d\n", i, counts[i]);
    }
    double sum = 0.0;
    for (int i : counts) {
      sum += i;
    }
    double avr = sum / 2000;
    System.out.println(avr);
  }
}

コンパイル

javac

結果

平均 4841445回
実行時間 5分52.508秒

エントリーNo.3 C++

#include <cstdio>
#include <cstdlib>
#include <ctime>
#include <numeric>

const int result[] = {0, 1, 2, 2, 1, 0, 1, 1, 1, 0, 0, 0, 2, 1};
 
int count() { 
  for (int i = 0; ; ++i) {
    int j;
    for (j = 0; j < 14; ++j) {
      if (result[j] != (std::rand() % 3)) {
        break;
      }
    }
    if (j == 14) {
      return i;
    }
  }
}
 
int main() {
  int counts[2000];
  std::srand(std::time(NULL));
  for (int i = 0; i < 2000; ++i) {
    counts[i] = count();
    std::printf("%04d %d\n", i, counts[i]);
  }
  double sum = std::accumulate(counts, counts + 2000, 0.0);
  double avr = sum / 2000;
  std::printf("%f\n", avr);
  return 0;
}

コンパイル

g++ -O3

結果

平均 4783978回
実行時間 6分7.338秒

エントリーNo.4 C言語

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

const int result[] = {0, 1, 2, 2, 1, 0, 1, 1, 1, 0, 0, 0, 2, 1};
int counts[2000];
 
int count() { 
  int i;
  for (i = 0; ; ++i) {
    int j;
    for (j = 0; j < 14; ++j) {
      if (result[j] != (rand() % 3)) {
        break;
      }
    }
    if (j == 14) {
      return i;
    }
  }
}

double accumulate() {
  int i;
  double sum;
  for (i = 0; i < 2000; ++i) {
    sum += counts[i];
  }
  return sum;
}
 
int main() {
  int i;
  srand(time(NULL));
  for (i = 0; i < 2000; ++i) {
    counts[i] = count();
    printf("%04d %d\n", i, counts[i]);
  }
  double sum = accumulate();
  double avr = sum / 2000;
  printf("%f\n", avr);
  return 0;
}

コンパイル

gcc -O3

結果

平均 4568117回
実行時間 5分49.178秒

結果

課題の仕様上平均がばらつくのでそこらへんがハンデになったりならなかったりして順位は付け辛かったりします。まぁD言語残当だとしても、このJavaの速さは一体なんなんでしょう。

追記:Javaのコードに冗長な箇所があったのでそれを削って再測定など。