首先考虑权值不算平方这么算,
这个很简单,直接 dp,设 \(f_{i,j}\) 是为到点 \((i,j)\) 结束的路径权值和,
那么转移就很简单了加上左边的上边的在加上两个 Y 所加上的新权。
那么平方怎么做,注意到 \((a+1)^2=a^2+2a+1\),直接类似的转移,在加上两倍一次权值即可。
const int N = 2e3 + 5;
int n, m;
string s[N];
mint C[N << 1][N << 1];
mint f[N][N][2];
void solve() {
cin >> n >> m;
FOR(i, 1, n) {
cin >> s[i];
s[i] = ' ' + s[i];
}
FOR(i, 0, max(n, m) << 1) {
C[i][0] = 1;
FOR(j, 1, i) {
C[i][j] = C[i - 1][j] + C[i - 1][j - 1];
}
}
FOR(i, 1, n) {
FOR(j, 1, m) {
f[i][j][0] = f[i - 1][j][0] + f[i][j - 1][0];
f[i][j][1] = f[i - 1][j][1] + f[i][j - 1][1];
if(s[i][j] == 'Y' && s[i - 1][j] == 'Y') {
f[i][j][0] += C[i + j - 3][j - 1];
f[i][j][1] += f[i - 1][j][0] * 2 + C[i + j - 3][j - 1];
}
if(s[i][j] == 'Y' && s[i][j - 1] == 'Y') {
f[i][j][0] += C[i + j - 3][i - 1];
f[i][j][1] += f[i][j - 1][0] * 2 + C[i + j - 3][i - 1];
}
}
}
cout << f[n][m][1] << endl;
}
标签:Square,int,YY,加上,权值,ARC157C
From: https://www.cnblogs.com/kevinlikescoding/p/18030311