题目
把n个骰子扔在地上,所有骰子朝上一面的点数之和为s。输入n,打印出s的所有可能的值出现的概率。
你需要用一个浮点数数组返回答案,其中第 i 个元素代表这 n 个骰子所能掷出的点数集合中第 i 小的那个的概率。
示例 1:
输入: 1
输出: [0.16667,0.16667,0.16667,0.16667,0.16667,0.16667]
思路
- dp数组表示共i个色子掷出s个点的次数。
- i个色子公有5*i+1种点数。
- dp[i][s]+=dp[i-1][s-j] //当前n个骰子出现的点数之和等于前一次出现的点数之和加上这一次出现的点数
代码
public double[] twoSum(int n) {
int [][]dp = new int[n+1][6*n+1];//表示i个色子掷出s个点的次数
for(int i = 1;i<=6;i++){
dp[1][i] = 1;//一个色子掷出所有次数都是1
}
for(int i=2;i<=n;i++){//色子个数
for(int s = i;s<=6*i;s++){//点数总数
for(int j = 1;j<=6;j++){//当前色子个数
//下面的公式数组越界判断
if(s-j<i-1) break;
dp[i][s] += dp[i-1][s-j];
}
}
}
//总次数
double total = Math.pow((double)6,(double)n);
//答案解的个数
double []ans = new double[5*n+1];//因为最大就只会出现5*n+1种点数
for(int i = n;i<=6*n;i++){
ans[i-n] = ((double)dp[n][i])/total;
}
return ans;
}