我們稱乙個長度為 2n 的數列是有趣的,當且僅當該數列滿足以下三個條件:
它是從 1 到 2n 共 2n 個整數的乙個排列 ;
所有的奇數項滿足 a
1
<
⋯
n−
1a_1a1
<
⋯n−1
,所有的偶數項滿足 a
2
<
⋯
na_2a2
<
⋯n;任意相鄰的兩項 a2i
−1
a_a2
i−1
與 a2ia_
a2i
(1 ≤i
≤n
1≤i≤n
1≤i≤
n) 滿足奇數項小於偶數項,即:a2i
−1
ia_a2
i−1
i。任務是:對於給定的 n,請求出有多少個不同的長度為 2n 的有趣的數列。
因為最後的答案可能很大,所以只要求輸出答案 modp 的值。
輸入格式
只包含用空格隔開的兩個整數 n 和 p。
輸出格式
僅含乙個整數,表示不同的長度為 2n 的有趣的數列個數 modp 的值。
資料範圍
1≤n≤106,
2≤p≤109
輸入樣例:
3 10
輸出樣例:
5樣例解釋
對應的 5 個有趣的數列分別為 ,,,,。
看到3,5的時候就應該往卡特蘭數那個方向想了。首先我們回憶下卡特蘭數的性質:滿足…序列中…的個數都不少於…的個數的序列有多少個。然後我們看這道題的擺列方式。寫幾個數可以發現1的位置一定是確定在奇數項位置的。然後再看後面的拜訪的時候,擺放的時候奇數項的個數一定要大於等於偶數項的個數,比如放5的時候,如果奇數項小於偶數項,那麼5前面的偶數項一定要小於等於奇數項,不然這其中的偶數項就會是5後面的某個數(比5大)。就不滿足情況了。
這裡因為p不是質數,所以我們直接用c2n
n−c2
nn−1
=c2n
n/n+
1c_^n-c_^=c_^n/n+1
c2nn−
c2nn
−1=
c2nn
/n+
1的前半部分來算,求組合數的時候用分解質因子+快速冪來求。
#include
#define int long long
using
namespace std;
const
int n=
2000010
;int n,p,prime[n]
,cnt,st[n]
;void
init
(int n)}}
intget
(int a,
int b)
intq_pow
(int a,
int k)
return res;
}intc(
int a,
int b)
return
(res+p)
%p;}
signed
main()
組合數學 求組合數
對於求組合數,要根據所給資料範圍來選擇合適的演算法 這道題中所給的資料範圍適合用打表的方法直接暴力求解 先用4e6的複雜度預處理出所有的情況,再用1e4的複雜度完成詢問即可 include using namespace std const int n 2010 const int mod 1e9 ...
數學 組合數學
mod must be a prime const int mod 1e9 7 namespace combinatory ll inv ll x ll fac maxn invfac maxn void initc int n ll a ll n,ll m ll c ll n,ll m ll d ...
組合數學筆記
從n個數中選m個數,每個數至多選一次,方案數 性質 c n,0 c n,n 1 c n,m c n,n m c n,m c n 1,m 1 c n 1,m 楊輝三角 二項式展開 x y n i 0.n c n,i x iy n i 那這裡先說一下楊輝三角 前提 每行端點與結尾的數為1 每個數等於它上...