问题描述:
扔n个骰子,第i个骰子有可能投掷出Xi种等概率的不同的结果,数字从1到Xi。所有骰子的结果的最大值将作为最终结果。求最终结果的期望。
输入描述:
第一行一个整数n,表示有n个骰子。(1 <= n <= 50) 第二行n个整数,表示每个骰子的结果数Xi。(2 <= Xi <= 50)
输出描述:
输出最终结果的期望,保留两位小数。
输入例子:
2 2 2
输出例子:
1.75
思路分析:
分析:这道题本身是蛮简单的,但比较难理解的是题意,主要考察概率论的知识。为了方便分析,我以三个骰子为例:例如Xi所给定的输入依次为:X1 = 3, X2 = 2,X3 = 3
那么我们可以取到的结果如下:
1 : 假设这三个骰子当中取到的最大值为1,则第一个骰子只能选择一种,第二个骰子只能选择一种,第三个骰子只能选择一种,即共有 1 * 1 * 1 = 1 种情况
2: 同理,假设这三个骰子当中取到的最大值为2, 则第一个骰子可以选择2种(1或者2),第二个骰子可以选择2种,第三个骰子可以选择2种,我们要排除 1 1 1 这种情况,因为当前取到的最大值为2,即至少有一个骰子取值为2,共有 2*2*2 - 1*1*1 = 7种可能
3:同理,假设这三个骰子当中取到的最大值为3,则第一个骰子可以选择3种(1或者2或者3),第二个骰子可以选择2种(最大值只能到2),第二个骰子可以选择3种,排除最大值为2的情况,即共有 3*2*3 - 2*2*2 = 10 种情况。
所有骰子出现的情况共有:3*2*3=18种。
取到1的可能性为: 1 / 18; 取到2的可能性为: 7 / 18;取到3的可能性为: 10 / 18;
根据高中概率论的知识即可求解出期望:1 * 1 / 18 + 2 * 7 / 18 + 3 * 10 / 18
特别注意的一点是:数据类型取double,int部分结果会溢出,而且很难找出原因。
代码实现:
import java.util.*;
public class Main{public static void main(String[] args) {Scanner sc = new Scanner(System.in);int m = 0;if(sc.hasNextLine())m = Integer.parseInt(sc.nextLine());//System.out.println(m);int[] numbers=new int[m];int count = 0;int max = 0;double res = 0;double pre=0;for(int i = 0; i < m;i++){int k = sc.nextInt();numbers[count++] = k;max=Math.max(max,k);}for(int i = 1; i <= max;i++){double temp = 1.0;for(int j = 0;j<m;j++){temp *= (double)Math.min(i,numbers[j])/numbers[j];}res += (temp-pre)*i;pre = temp;}System.out.println(String.format("%.2f", res));}
}