H - Unloaded Die Gym - 101652U

Consider a six-sided die, with sides labeled 1 through 6. We say the die is fair if each of its sides is equally likely to be face up after a roll. We say the die is loaded if it isn’t fair. For example, if the side marked 6 is twice as likely to come up as than any other side, we are dealing with a loaded die. For any die, define the expected result of rolling the die to be equal to the average of the values of the sides, weighted by the probability of those sides coming up. For example, all six sides of a fair die are equally likely to come up, and thus the expected result of rolling it is (1 + 2 + 3 + 4 + 5 + 6)/6 = 3.5. You are given a loaded die, and you would like to unload it to make it more closely resemble a fair die. To do so, you can erase the number on one of the sides, and replace it with a new number which does not need to be an integer or even positive. You want to do so in such a way that • The expected result of rolling the die is 3.5, just like a fair die. • The difference between the old label and the new label on the side you change is as small as possible. Input The input consists of a single line containing six space-separated nonnegative real numbers v1 . . . v6, where vi represents the probability that side i (currently labeled by the number i) is rolled. It is guaranteed that the given numbers will sum to 1. Output Print, on a single line, the absolute value of the difference between the new label and old label, rounded and displayed to exactly three decimal places

题意:给你六个实数,分别对应着筛子六个面出现的概率,每个面上的数值分别是1,2,3,4,5,6,询问想让他变成一个公平的筛子(这里是指将每个面上的(数值×概率)相加等于3.5),将某个面上的数值(注意 不是概率)改变,使它改变后的数值与改变前的数值差距(绝对值)最小。

很容易分析出来,我们想要改变的数值差最小,当然是要选择概率最大的那个面来改变,我们只需要先将六个面的概率sort一下,这里建议使用结构体将每个面的概率和数值保存一下,这样sort的时候可以一起改变,然后将概率最大的那个面,根据公式算一下结果等于3.5,可以推一下公式,很简单。

#include <bits/stdc++.h>

using namespace std;

struct node
{
    float pp;
    int p;
}f[10];
bool cmp(struct node a,struct node b)
{
    return a.pp>b.pp;
}
float ff(float x)//别忘了差值要求的是绝对值
{
    if(x<0)
        return -x;
    else
        return x;
}
int main()
{
    int i;
    for(i=1;i<=6;i++)
    {
        scanf("%f",&f[i].pp);
        f[i].p=i;
    }
    sort(f+1,f+7,cmp);
    float sum=0;
    for(i=1;i<=6;i++)//将每个面的概率×数值加起来
    {
        sum=sum+f[i].p*f[i].pp;
    }
    float k;
    k=(3.50-sum+(f[1].p*f[1].pp))/f[1].pp;
    printf("%.3f",ff(k-f[1].p));
    return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值