AGC 053 C Random Card Game 题解
Posted Gary2005
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了AGC 053 C Random Card Game 题解相关的知识,希望对你有一定的参考价值。
AGC 053 C Random Card Game 题解
容易发现最终被消除的牌堆一定是不包含\\(2n\\)的。
设不包含\\(2n\\)的牌堆为B,包含\\(2n\\)的牌堆为\\(A\\)。
最优策略如下:
- 若存在一个\\(k\\)满足\\(B_k<A_k\\),则进行操作\\(k\\)。
- 否则进行操作\\(1\\)。
容易发现答案是\\(\\max(0,\\max\\{d_i-i\\})+n\\),\\(d_i\\)是最小的满足\\(A_j>B_i\\)的\\(j\\)。
所以可以枚举答案\\(\\leq k\\),也就是\\(\\exists_{j\\in [1,i+k]} A_j>B_i\\)。
贡献为:
\\[i!\\cdot (i+1)\\cdot (i+1)\\cdot (i+3)\\cdot (i+3)...(2n-i-1)\\cdot (2n-i-1)\\cdot [(2n-i)\\cdot...\\cdot(n-1)]
\\]
可以预处理之后\\(O(1)\\)计算。
code:
/*
{
######################
# Author #
# Gary #
# 2021 #
######################
*/
#include<bits/stdc++.h>
#define rb(a,b,c) for(int a=b;a<=c;++a)
#define rl(a,b,c) for(int a=b;a>=c;--a)
#define LL long long
#define IT iterator
#define PB push_back
#define II(a,b) make_pair(a,b)
#define FIR first
#define SEC second
#define FREO freopen("check.out","w",stdout)
#define rep(a,b) for(int a=0;a<b;++a)
#define SRAND mt19937 rng(chrono::steady_clock::now().time_since_epoch().count())
#define random(a) rng()%a
#define ALL(a) a.begin(),a.end()
#define POB pop_back
#define ff fflush(stdout)
#define fastio ios::sync_with_stdio(false)
#define check_min(a,b) a=min(a,b)
#define check_max(a,b) a=max(a,b)
using namespace std;
//inline int read(){
// int x=0;
// char ch=getchar();
// while(ch<\'0\'||ch>\'9\'){
// ch=getchar();
// }
// while(ch>=\'0\'&&ch<=\'9\'){
// x=(x<<1)+(x<<3)+(ch^48);
// ch=getchar();
// }
// return x;
//}
const int INF=0x3f3f3f3f;
typedef pair<int,int> mp;
/*}
*/
const int MOD=1e9+7;
const int MAXN=2e6+233;
int fact[MAXN],calc[MAXN],ifact[MAXN],fact2[MAXN],ifact2[MAXN];
int quick(int A,int B){
if(B==0) return 1;
int tmp=quick(A,B>>1);
tmp=1ll*tmp*tmp%MOD;
if(B&1) tmp=1ll*tmp*A%MOD;
return tmp;
}
int inv(int A){return quick(A,MOD-2);}
int main(){
fill(fact,fact+MAXN,1);
fill(ifact,ifact+MAXN,1);
fill(fact2,fact2+MAXN,1);
fill(ifact2,ifact2+MAXN,1);
rb(i,1,2000000){
fact[i]=1ll*fact[i-1]*i%MOD;
if(i>=2)
fact2[i]=1ll*fact2[i-2]*i%MOD;
else
fact2[i]=i;
}
ifact[2000000]=inv(fact[2000000]);
ifact[2000000-1]=inv(fact[2000000-1]);
ifact2[2000000-1]=inv(fact2[2000000-1]);
ifact2[2000000]=inv(fact2[2000000]);
rl(i,2000000-2,1){
ifact[i]=1ll*ifact[i+1]*(i+1)%MOD;
ifact2[i]=1ll*ifact2[i+2]*(i+2)%MOD;
}
int n;
scanf("%d",&n);
rb(i,0,n-1){
calc[i]=fact[i];
calc[i]=1ll*calc[i]*fact2[2*n-i-1]%MOD*ifact2[max(0,i-1)]%MOD;
calc[i]=1ll*calc[i]*fact2[2*n-i-1]%MOD*ifact2[max(0,i-1)]%MOD;
calc[i]=1ll*calc[i]*fact[2*n-1]%MOD*ifact[2*n-i-1]%MOD;
}
int rest=0;
rb(i,1,n-1){
(rest+=1ll*i*(MOD+calc[i]-calc[i-1])%MOD)%=MOD;
}
rest=1ll*rest*ifact[2*n]%MOD;
rest=2ll*rest%MOD;
(rest+=n)%=MOD;
cout<<rest<<endl;
return 0;
}
以上是关于AGC 053 C Random Card Game 题解的主要内容,如果未能解决你的问题,请参考以下文章
c_cpp http://www.gamasutra.com/view/feature/3383/simple_intersection_tests_for_games.php