Вероятность в течение многих игр - PullRequest
1 голос
/ 01 февраля 2011

Я работаю над проблемой проекта Эйлера № 205, в которой говорится:

У Питера есть девять четырехгранных (пирамидальных) костей, каждая с гранями 1, 2, 3, 4. У Колинашесть шестигранных (кубических) кубиков, каждый с гранями, пронумерованными 1, 2, 3, 4, 5, 6.

Питер и Колин бросают свои кости и сравнивают итоги: самые высокие общие выигрыши.Результатом является ничья, если общие суммы равны.

Какова вероятность того, что Пирамидальный Пит победит Кубического Колина?Дайте ответ, округленный до семи знаков после запятой в форме 0.abcdefg

Моя первая попытка (ниже) включала в себя 1000 «игр», где в каждой игре было 1 000 000 ходов.Затем берём среднее по всем играм.Я последовательно получаю результаты в области .559, но когда ответ должен быть до 7 десятичных знаков, это не так близко.

public class pe205 {

    public static void main(String[] args) {

        pe205 p = new pe205();

        double sum = 0.0;

        for(int i=0; i < 1000; i++){
            sum += p.determineProbability();
        }

        System.out.println(sum/1000.0);

    } // end main

    public double determineProbability(){

        int peterWins = 0;
        int colinWins = 0;

        for(int i=0; i < 1000000; i++){

            int peterSum = 0;
            for(int j=0; j < 4; j++){
                Random r = new Random();
                peterSum += r.nextInt(9);
            }

            //System.out.println(peterSum);

            int colinSum = 0;
            for(int j=0; j < 6; j++){
                Random r = new Random();
                colinSum += r.nextInt(6);
            }

            //System.out.println(colinSum);

            if(peterSum > colinSum){
                peterWins++;
            }
            if(colinSum > peterSum){
                colinWins++;
            }

        }
        double peteBeatsColin = (double)peterWins/(double)(colinWins + peterWins);

        return peteBeatsColin;

    }

} // end class

Я читал о методе Монте-Карло.Будет ли это ситуация, когда это будет полезно, и если да, может ли кто-нибудь дать мне краткий обзор?Или я упускаю какое-то довольно очевидное математическое решение?

Я хотел бы сказать, что мне нравится решать эти проблемы, и я не ищу ответа, просто небольшой толчок вправильное направление.

Ответы [ 4 ]

2 голосов
/ 01 февраля 2011

Сначала напишите функцию, которая вычисляет вероятность N S-сторонних костей, приводящих к заданному значению C.

Получив это, напишите функцию, чтобы сложить вероятность того, что данный набор костейбудет бросать меньше определенного числа.

Как только вы это сделаете, напишите функцию, которая зацикливается на n->(n*s) и вычисляет вероятность того, что другой набор кубиков будет меньше или равен этому.

Помните, что вероятность A и B, если они не запутаны, равна P(A) * P(B).

2 голосов
/ 01 февраля 2011

Хорошо, я понял это. Точное решение возможно. Вот толчок.

Петр может бросить 9 до 36.

Колин может бросить от 6 до 36.

Рассчитайте вероятность того, что Питер может бросить r, где r колеблется от 9 до 36.

Сделайте то же самое для Колина, r в диапазоне от 6 до 36.

Отсюда вы можете рассчитать вероятность того, что Питер победит Колина.

2 голосов
/ 01 февраля 2011

Почему бы не попытаться посчитать результат комбинаторно?Явно рассчитать результат, добавив условия вида

a_i = P(peter throws i, Colin throws < i)
0 голосов
/ 01 февраля 2011
double colin(int n)
{
  int t = 0;
  for(int d1 = 1; d1<7; d1++)
  for(int d2 = 1; d2<7; d2++)
  for(int d3 = 1; d3<7; d3++)
  for(int d4 = 1; d4<7; d4++)
  for(int d5 = 1; d5<7; d5++)
  for(int d6 = 1; d6<7; d6++)
  if(d1+d2+d3+d4+d5+d6 == n)
  t++;
  return ((double)t)/(6*6*6*6*6*6);
}

- * Это если у Питера только 4 кубика, а не девять, я ленивый *

double peter(int n)
{
  int t = 0;
  for(int d1 = 1; d1<5; d1++)
  for(int d2 = 1; d2<5; d2++)
  for(int d3 = 1; d3<5; d3++)
  for(int d4 = 1; d4<5; d4++)
  if(d1+d2+d3+d4 == n)
  t++;
  return ((double)t)/(4*4*4*4);
}
main()
{
  double r = 0.0;
  for(int c = 4; c < 16; c++){
    for(int p = 6; p < 36; p++){
      if(c > p){
        r += colin(c)*peter(p);
      }
    }
  }
  System.out.println(r);
}

Прошу прощения за крайнюю неэффективность, но вы поняли.

...