Educational Codeforces Round 79 D Santa's Bot

 
 

被教育场

题意:先等概率选一个人,再从他想要礼物里等概率选一个,再独立于前两次选择,选一个人,他想要的礼物也被选中,则该组合有效,求组合有效的分数概率(模意义下)

玩一下两个样例应该就能出来知道咋算,虽然我第一个样例是跑了两重循环得出 7/8,拼凑起来才勉强理解的题意。

但知道咋算不一定会code啊。

我就是啊。

模拟了分数的加法乘法运算,通分约分,肯定要WA啊,因为到后面分子分母越来越大存不下。

但实际上,两个分数在某个模数意义下相加可以直接转化,即   x/y+u/v  == x*inv(y) +u*inv(v)

证明我也不会呀

这辈子不可能去证明的

理解还是好理解的

此处由于模数是质数,直接由费马小定理得到逆元来算就行了

 1 #include <bits/stdc++.h>
 2 
 3 #ifndef ONLINE_JUDGE
 4 #define debug(x) cout << #x << ": " << x << endl
 5 #else
 6 #define debug(x)
 7 #endif
 8 
 9 using namespace std;
10 typedef long long ll;
11 const int MAXN=1e6+7;
12 const int INF=0x3f3f3f3f;
13 const int MOD=998244353;
14 
15 
16 vector<int>a[MAXN];
17 int cnt[MAXN];
18 
19 ll quick(ll x,ll n)  //¿ìËÙÃÝ x^n
20 {
21     ll res=1;
22     while(n)
23     {
24         if(n&1) res=(res*x)%MOD;
25         x=(x*x)%MOD;
26         n>>=1;
27     }
28     return res;
29 }
30 
31 ll inv(ll a)
32 {
33     return quick(a,MOD-2);
34 }
35 
36 int main()
37 {
38     ios::sync_with_stdio(false);
39     cin.tie(0);
40     int n;
41     cin>>n;
42     for(int i=0;i<n;++i)
43     {
44         int k;
45         cin>>k;
46         while(k--)
47         {
48             int tt;
49             cin>>tt;
50             a[i].push_back(tt);
51             cnt[tt]++;
52         }
53     }
54     ll ans=0;
55     for(int i=0;i<n;++i)
56     {
57         int q=a[i].size();
58         ll tmp=0;
59         for(auto u:a[i])
60             tmp+=cnt[u];
61         ll cur=inv(1ll*n*n%MOD*q%MOD)*tmp%MOD;
62         ans+=cur;
63         debug(ans);
64         debug(tmp);
65         ans%=MOD;
66     }
67     cout<<ans<<endl;
68     return 0;
69 }
View Code
原文地址:https://www.cnblogs.com/Zzqf/p/12111235.html