ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

「国家集训队」单选错位 题解

2022-06-11 19:31:52  阅读:140  来源: 互联网

标签:frac min int 题解 d% 单选 答案 max 国家集训队


「国家集训队」单选错位 题解

题目大意

试卷上共有 $ n $ 道单选题,第 $ i $ 道题有 $ a_i $ 个选项,每个选项成为正确答案的概率都是相等的

$ A $ 全部做对,但抄错位了:每题都向后抄了一个位置,特别地,第 $ n $ 道题目抄到了第 $ 1 $ 道题目的位置

$ A $ 想知道自己期望能做对几道题目。

输入

输入只有 5 个整数参数 $ n, A, B, C, a_1 $ ,由上交的程序产生数列 $ a $ 。

scanf("%d%d%d%d%d",&n,&A,&B,&C,a+1);
	for(int i=2;i<=n;i++)
		a[i]=((long long)a[i-1]*A+B)%100000001;
	for(int i=1;i<=n;i++)
		a[i]=a[i]%C+1;

可以通过以上的程序语句得到 $ n $ 和数列 $ a $。

输出

$ A $ 期望做对的题目数,保留三位小数

样例及解释

输入

3 2 0 4 1

输出

1.167

解释

$ a={2,3,1} $ ,表示第 $ 1 $ 题有 $ 2 $ 个选项,第 $ 2 $ 题有 $ 3 $ 个选项,第 $ 3 $ 题有 $ 1 $ 个选项。


正确答案 A的答案 做对题目 出现概率
$ {1,1,1} $ $ {1,1,1} $ $ 3 $ $ \frac{1}{6} $
$ {1,2,1} $ $ {1,1,2} $ $ 1 $ $ \frac{1}{6} $
$ {1,3,1} $ $ {1,1,3} $ $ 1 $ $ \frac{1}{6} $
$ {2,1,1} $ $ {1,2,1} $ $ 1 $ $ \frac{1}{6} $
$ {2,2,1} $ $ {1,2,2} $ $ 1 $ $ \frac{1}{6} $
$ {2,3,1} $ $ {1,2,3} $ $ 0 $ $ \frac{1}{6} $

共有 $ 6 $ 种情况,每种情况出现的概率是 $ \frac{1}{6} $ ,A 期望做对 $ \frac{3+1+1+1+1+0}{6} = \frac{7}{6} $ 题,保留三位小数即 $ 1.167 $ 。

思路

算法选择

数据范围 $ n \le 10^7 $ ,说明需要 $ O(n) $ 的算法解决。推测是递推贪心公式

深入思考

通过样例仔细观察后,我们可以发现,第 $ i $ 题是否正确,只与第 $ i-1 $ 题的答案是否跟第 $ i $ 题相同有关。所以可以选择公式法。


举个例子:

$ a={2,3,1} $

对于第 $ 1 $ 题和第 $ 2 $ 题,正确答案的总情况数为 $ a[1] \times a[2] = 6 $ ,而两道题答案相同的只有 $ min(a[1],a[2]) = 2 $ 种。最终做对的概率为 $ \frac{min(a[1],a[2])}{a[1] \times a[2]} = \frac{1}{3} $ 。

为什么要求最小值?

因为当第二题答案为 3 时,第一题答案不可能与它相同。所以相同情况数取决于它们的最小值。

由上可得:两道题的正确答案情况总数为 $ a[i] \times a[i-1] $ ,两道题答案相等的情况有 $ min(a[i],a[i-1]) $ 种,所以答案需要加上一个 $ \frac{min(a[i],a[i-1])}{a[i] \times a[i-1]} $ 。

化简一下:

$ \ \ \ \ \ \frac{min(a[i],a[i-1])}{a[i] \times a[i-1]} $

$ = \frac{1}{max(a[i],a[i-1])} $

注意,这里的 $ min $ 变成了 $ max $ 。

  1. 当 $ min(a[i],a[i-1]) = a[i] $ 时,原式变为 $ \frac{1}{a[i-1]} $ ;

  2. 当 $ min(a[i],a[i-1]) = a[i-1] $ 时,原式变为 $ \frac{1}{a[i]} $ 。

综合一下,就是 $ \frac{1}{max(a[i],a[i-1])} $ 。

对于特殊情况只需要再加上 $ \frac{1}{max(a[n],a[1])} $ 即可。

最终公式为:

$ ans = \frac{1}{max(a[n],a[1])} + \underset{i = 2}{\overset{n}{\sum}} \frac{1}{max(a[i],a[i-1])} $

因此,代码出。

代码实现

注释版本

#include<bits/stdc++.h>
#define ll int
const ll N=10000010;//1e7+10 
using namespace std;

ll n,A,B,C,a[N];
double ans;//答案 

int main(){
	
	scanf("%d%d%d%d%d",&n,&A,&B,&C,a+1);
	for(int i=2;i<=n;i++)
		a[i]=((long long)a[i-1]*A+B)%100000001;
	for(int i=1;i<=n;i++)
		a[i]=a[i]%C+1;
	
	for(ll i=2;i<=n;i++){//是2~n 
		ans+=1.0/max(a[i],a[i-1]);//公式 
	}
	ans+=1.0/max(a[n],a[1]);//特殊处理 
	printf("%.3lf",ans);//输出 
	
	return 0;
}

压行版本

???

#include<bits/stdc++.h>
const int N=100000001;
using namespace std;
int n,A,B,C,a[N],i=1;
double ans;
main(){
	scanf("%d%d%d%d%d",&n,&A,&B,&C,a+1);
	for(;++i<=n;)a[i]=((long long)a[i-1]*A+B)%N;
	for(i=0;++i<=n;)(a[i]%=C)+=1;
	for(i=1;++i<=n;)ans+=1.0/max(a[i],a[i-1]);
	ans+=1.0/max(a[n],a[1]);
	printf("%.3lf",ans);
}

尾声

如果你发现了问题,你可以直接回复这篇题解

如果你有更好的想法,也可以直接回复!

标签:frac,min,int,题解,d%,单选,答案,max,国家集训队
来源: https://www.cnblogs.com/zsc985246/p/16366596.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有