首页 > 其他分享 >P8386 [PA2021] Od deski do deski 题解

P8386 [PA2021] Od deski do deski 题解

时间:2023-12-19 12:11:19浏览次数:21  
标签:do int 题解 合法 deski 序列 times dp define

显然是一道计数 dp。

dp 状态应该是最难的一部分了,个人认为这种状态设计得比较巧妙。如果像我刚开始一样设 \(dp_{i,j}\) 表示序列中一共有 \(i\) 个数,序列最后一个数为 \(j\) 的合法方案数的话,那么方程就会变得很不好转移,因为我们不知道当前的 \(j\) 和之前的某些数能不能匹配上,所以我们可以改变状态为 \(dp_{i,j}\) 表示序列中一共有 \(i\) 个数,在当前情况的序列后面加 \(j\) 种数能使序列变为合法序列的方案数。但是有一个问题,就是我们不知道当前合不合法,于是可以再加一维 \(0/1\) 表示当前合法或者不合法。

然后就是状态的转移了。首先需要知道两个很显然的性质:

  • 如果在序列后面加 \(j\) 种数可以使序列变的合法,那么加另外 \(m-j\) 种数就会变得不合法。

  • 并且如果序列 \(S\) 是合法的,那么形如 \(S+x+T+x\) 的序列一定是合法的,形如 \(S+x+T\) 的序列一定是不合法的,其中 \(T\) 是不包含 \(x\) 的任意序列。

于是就可以用刷表法进行转移了,具体转移方程如下:

\(\begin{cases}dp_{i+1,j,1}+=dp_{i,j,1}\times j \\dp_{i+1,j+1,0}+= dp_{i,j,1}\times (m-j) \\dp_{i+1,j,0}+=dp_{i,j,0}\times (m-j) \\dp_{i+1,j,1}+=dp_{i,j,0}\times j \end{cases}\)

Code

#include<bits/stdc++.h>
using namespace std;
#define int long long
#define inf 0x3f
#define inf_db 127
#define ls id << 1
#define rs id << 1 | 1
#define re register
#define endl '\n'
typedef pair <int,int> pii;
const int MAXN = 3e3 + 10;
const int mod = 1e9 + 7;
int n,m,dp[MAXN][MAXN][2],ans;
signed main()
{
	cin >> n >> m;
	dp[0][0][1] = 1;
	for(int i = 0;i < n;i++)
		for(int j = 0;j <= i;j++)
		{
			dp[i + 1][j][1] = (dp[i + 1][j][1] + dp[i][j][1] * j) % mod;
			dp[i + 1][j + 1][0] = (dp[i + 1][j + 1][0] + dp[i][j][1] * (m - j)) % mod;
			dp[i + 1][j][0] = (dp[i + 1][j][0] + dp[i][j][0] * (m - j)) % mod;
			dp[i + 1][j][1] = (dp[i + 1][j][1] + dp[i][j][0] * j) % mod;
		}
	for(int i = 0;i <= n;i++) ans = (ans + dp[n][i][1]) % mod;
	cout << ans;
	return 0; 
}

标签:do,int,题解,合法,deski,序列,times,dp,define
From: https://www.cnblogs.com/Creeperl/p/17913424.html

相关文章

  • C0328 【1005 C组】模拟测试 斜率 题解
    原题链接:斜率。题意在一个平面直角坐标系中,给定\(n\)个点的横纵坐标,求出哪两个点所构成的连线的斜率最接近\(\frac{P}{Q}\)。数据范围:\(n\le1000000\)。思路显然这是一道数学题,不能直接暴力去找答案。首先我们可以弱化一下题目,求出斜率最接近\(y=0\)即\(x\)轴的两......
  • Omkar and Akmar 题解
    题意:有一个\(n\)个点的环,以及两个人。每个人可以向环中任意一个位置放置一个\(A\)或者\(B\),但是相邻的位置不能相同,不能行动者输。问最终的局面有多少种。一个结论是:后手必胜。证明:最终肯定不可能出现两个连续的空格,否则一定可以在其中一个上填\(A\)或\(B\)。所以最多只......
  • Square-free division (easy version) 题解
    题意:给定一个长度为\(n\)的序列,求最少能将这个序列分成多少段使得任意一段中不存在两个数的积为完全平方数。一个小Trick:如果两个数乘起来为平方数,可以先将每个数的平方因子除掉,然后这两个数必然相等。于是这道题被转化为了一个区间不能有相等的值,这就很典了。设\(pos_{a_{i......
  • Animals and Puzzle 题解
    原题链接:CF713D题意:给定一个\(n\timesm\)的地图\(a\),\(a_{i}\)为\(0\)或\(1\)。有\(t\)次询问,每次询问给定一个矩形,求出这个矩形中最大的由\(1\)构成的正方形的边长是多少。首先考虑预处理出\(d_{i,j}\)表示以\((i,j)\)为左上角的最大正方形边长是多少。对于每......
  • C0392 B 【1109 B组】预处理器 题解
    题意:求有多少个长度为\(n\)的数组\(a\)满足以下条件。条件一:\(l_{i}\lea_{i}\ler_{i}\)。条件二:\(a_{i}\)模\(2\)等于\(p_{i}\)。条件三:\(s\le\suma_{i}\let\)。求答案模\(mod\)的值,\(mod\)不一定是一个质数。数据范围:\(n\le13\)。又积累到一......
  • A Simple Task 题解
    这道题比较简单,简述一下思路。考虑状压\(DP\)。设\(dp_{i,j}\)表示走到第\(i\)个点,之前走过的点的状态为\(j\)的环的数量。这里有一个细节,就是我们都钦定每个走过的第一点是整个状态中编号最小的点,这样不会重复计算。考虑如何进行转移。如果当前点的编号比走过的最小编......
  • Maix II Dock 的USB OTG 及USB UART 测试
    1、通过USBOTG接口实现ADB的终端交互①、使用typeC数据线连接电脑和MaixIIDock板卡的USBOTG接口②、电脑弹窗并识别MaixIIDock板卡为一个“U盘”,如果提示U盘驱动有问题,请忽略。          ③、进入U盘可以看到对应的配置文件及一个app执......
  • CF1900D Small GCD 题解
    原题链接:CF1900D,题意不多赘述。首先可以将\(a\)数组排序,并且枚举中间的那个数\(a_i\)。那么答案就是\(\sum_{j=1}^{i-1}\gcd(a_j,a_i)\times(n-i)\)。重点在于求前面的\(\gcd\)。可以用欧拉反演,但是也可以不用,因为我不会。假设我们当前已经枚举到了\(a_i\),设\(f_k\)表......
  • CF1902D Robot Queries 题解
    题意:有一个二维平面直角坐标系,给定一串向某个方向移动\(1\)个单位的操作。有\(q\)个询问,对于每个询问给定\(x,y,l,r\),问如果倒着做\(l\)到\(r\)这段区间中的操作,是否会经过\((x,y)\)。ds题。先预处理出\(sx_i,sy_i\)表示执行完操作\(i\)后的位置,如果在\([l,r]\)......
  • 华中师范大学2023新生赛 H 龙 题解
    Link华中师范大学2023新生赛H龙Question有\(m\)个宝石孔,有\(n\)个宝石,每个宝石可以提升\(a_i\)点战斗力每次镶嵌一个宝石,被选中的宝石会随机选择一个宝石孔进去,如果这个孔原来有宝石,则原来的宝石会被损坏你可以任意决定镶嵌宝石的顺序,她想知道,如果把着\(n\)颗宝......