日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

nowcoder 提高组模拟赛 选择题 解题报告

發布時間:2025/6/17 编程问答 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 nowcoder 提高组模拟赛 选择题 解题报告 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

選擇題

鏈接:

https://www.nowcoder.com/acm/contest/178/B

來源:牛客網

題目描述

有一道選擇題,有 \(a,b,c,d\) 四個選項。

現在有 \(n\) 個人來做這題,第 \(i\) 個人有 \(p_{i,j}\) 的概率選第 \(j\) 個選項。

定義 \(cnt(x)\) 為選第 \(x\) 個選項的人數。

\(mx\)\(cnt(x)\) 最大的 \(x\) (如果有多個\(cnt(x)\)最大的 \(x\),則取其中 \(x\) 最小的),

\(cnt(mx) \le \lfloor\frac{n}{2}\rfloor\) ,則所有人得 \(0\) 分;

否則令 \(choice_i\) 表示第 \(i\) 個人選的選項,則第 \(i\) 人得\(w_{mx,choice_i}\)

求每個人的期望得分。

輸入描述:

第一行一個整數 \(n\) ,表示人數。

接下來 \(n\) 行,每行 \(4\) 個整數,其中第 \(i\) 行第 \(j\) 個數表示 \(p_{i,j}\) ,即在模 \(998244353\) 意義下第 \(i\) 個人選第 \(j\) 個選項的概率。

接下來 \(4\) 行,每行 \(4\) 個整數,第 \(i\) 行第 \(j\) 個數表示 \(w_{i,j}\)

輸出描述:

\(n\) 行,第 \(i\) 行表示第 \(i\) 個人在模 \(998244353\) 意義下的期望得分。

備注:

全部的輸入數據滿足:

  • \(1 ≤ n ≤ 2000\)
  • $0 ≤ p_{i,j} < 998244353 (1 ≤ i ≤ n,1 ≤ j ≤ 4) $
  • \(\sum\limits_{j=1}^4 p_{i,j} \equiv 1 (\bmod 998244353)(1\le i \le n)\)

各個測試點的性質如下

測試點編號n特殊性質
\(1\)\(\le 2\)
\(2\)\(\le 10\)\(p_{i,3}=p_{i,4}=0,(1\le i \le n)\)
\(3\)\(\le 10\)
\(4,5\)\(\le 100\)\(p_{i,3}=p_{i,4}=0,(1\le i \le n)\)
\(6,7\)\(\le 100\)\(p_{i,4}=0(1\le i \le n)\)
\(8,9,10,11\)\(\le 100\)
\(12\sim20\)\(\le 2000\)

Solution

考試的時候打了55pts暴力,結果爆5了,原因竟然是出負數了沒模正。。

枚舉每個人選什么和最后結果是什么,然后算一下其他人的選擇對這個結果的概率。

每次可以簡單的\(n^2\)\(dp\)

\(dp_{i,j}\)代表前\(i\)個人有\(j\)個選了的和

\(dp_{i,j}=dp_{i-1,j-1}p_{i,k}+dp_{i-1,j}(1-p_{i,k})\)

發現每次只是少了一個人不進行\(dp\)

可以先把所有人的\(dp\)搞出來,然后\(O(n)\)把人踢出來

具體的,設\(dp_{i}\)\(i\)個人選了某選項的全集

枚舉每個人時,顯然有\(dp_i'=p_idp_{i-1}+(1-p_i)dp_i\)

那么回退時有\(dp_i=\frac{dp_i'-p_idp_{i-1}}{1-p_i}\)

注意壓維了的話是存在順序的,還要特判\(p_i=1\)


Code:

#include <cstdio> #define ll long long const int N=2e3+10; const ll mod=998244353ll; int n; ll p[N][5],w[5][5],dp[N][5],inv[N][5],ans[N]; ll quickpow(ll d,ll k) {ll f=1;d=(d%mod+mod)%mod;while(k){if(k&1) f=f*d%mod;d=d*d%mod;k>>=1;}return f; } int main() {scanf("%d",&n);for(int i=1;i<=n;i++)for(int j=1;j<=4;j++)scanf("%lld",&p[i][j]),inv[i][j]=quickpow(1-p[i][j],mod-2);for(int i=1;i<=4;i++)for(int j=1;j<=4;j++)scanf("%lld",&w[i][j]);dp[0][1]=dp[0][2]=dp[0][3]=dp[0][4]=1;for(int k=1;k<=4;k++)for(int i=1;i<=n;i++){ll p1=(1-p[i][k]),p2=p[i][k];for(int j=n;j;j--)dp[j][k]=(p2*dp[j-1][k]+p1*dp[j][k])%mod;dp[0][k]=dp[0][k]*(1-p[i][k])%mod;}for(int i=1;i<=n;i++)//這個人for(int j=1;j<=4;j++)//選啥{if(p[i][j]==0) continue;for(int k=1;k<=4;k++)//結果是{if(w[k][j]==0) continue;int flag=1,up=(n>>1)+1-(j==k);ll sum=0;if(p[i][k]==1) flag=0;if(flag){dp[0][k]=dp[0][k]*inv[i][k]%mod;ll p2=p[i][k];for(int l=1;l<up;l++)//退包dp[l][k]=(dp[l][k]-p2*dp[l-1][k])%mod*inv[i][k]%mod;for(int l=up;l<=n;l++){dp[l][k]=(dp[l][k]-p2*dp[l-1][k])%mod*inv[i][k]%mod;sum+=dp[l][k];}}if(!flag){for(int i=up+1;i<=n;i++)sum+=dp[i][k];}sum%=mod;(ans[i]+=w[k][j]*sum%mod*p[i][j])%=mod;if(flag){ll p1=(1-p[i][k]),p2=p[i][k];for(int l=n;l;l--)dp[l][k]=(dp[l][k]*p1+p2*dp[l-1][k])%mod;dp[0][k]=dp[0][k]*(1-p[i][k])%mod;}}}for(int i=1;i<=n;i++)printf("%lld\n",(ans[i]+mod)%mod);return 0; }

2018.10.21

轉載于:https://www.cnblogs.com/butterflydew/p/9827273.html

總結

以上是生活随笔為你收集整理的nowcoder 提高组模拟赛 选择题 解题报告的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。