1.​​题目链接​​。其实这也是卡特兰数的一个定义,也可以转化为进出栈问题。就是求一下Cantalan数的第n项。由于比较大,可以采用质因子分解统计贡献来计算。

#include<bits/stdc++.h>
#define N 2000003
#define LL long long
using namespace std;
LL prime[N], pd[N], num[N], mp[N];
int n, p;
void init()
{
for (int i = 2; i <= 2000000; i++) {
if (!pd[i]) prime[++prime[0]] = i, mp[i] = prime[0];
for (int j = 1; j <= prime[0]; j++) {
if (prime[j] * i > 2000000) break;
pd[prime[j] * i] = 1;
if (i % prime[j] == 0) break;
}
}
}

void calc(int x, int val)
{
int k = x;
for (int i = 1; prime[i] * prime[i] <= k; i++)
if (k % prime[i] == 0) {
while (k % prime[i] == 0) {
k /= prime[i]; num[i] += val;
}
}
if (k > 1) num[mp[k]] += val;
}
LL qpow(LL a, LL b)
{
LL res = 1;
while (b)
{
if (b & 1)res = res * a % p;
a = a * a % p;
b >>= 1;
}
return res;
}
int main()
{
scanf("%d%d", &n, &p);
init();
for (int i = n + 1; i <= 2 * n; i++) calc(i, 1);
for (int i = 1; i <= n; i++) calc(i, -1);

calc(n + 1, -1);
LL ans = 1;
for (int i = 1; i <= prime[0]; i++)
ans = ans * qpow((LL)prime[i], num[i]) % p;
printf("%lld\n", ans);
}