非 dp 做法 WA #16 求调
查看原帖
非 dp 做法 WA #16 求调
362750
TernaryTree楼主2023/8/3 15:44
#include <bits/stdc++.h>
#define int long long

using namespace std;

const int maxn = 2e5 + 10;
const int mod = 0x3b800001;

int t, n, m, k;
int a[maxn];
int b[maxn];
int p[maxn];
int invk;

int power(int a, int b) {
	int t = 1;
	while (b) {
		if (b & 1) t = t * a % mod;
		a = a * a % mod, b >>= 1;
	}
	return t;
}

int calc(int n, int l, int r) {
	if (!l && !r) return p[n - 1] * k % mod;
	if (!l || !r) return p[n] % mod;
	int sig = n & 1 ? -1 : 1;
	int tot = (p[n - 1] + sig + mod) * invk % mod;
	if (l == r) {
		return (k - 1) * (p[n - 1] - tot) % mod * (tot - sig) % mod;
	} else {
		return ((k - 2) * (p[n - 1] - tot) % mod * (tot - sig) % mod + tot * (k - 1) % mod) % mod;
	}
}

int solve(int * a, int n) {
	int s = -1, ans = 1;
	for (int i = 1; i <= n; i++) {
		if (a[i] == -1 && s == -1) s = i;
		else if (a[i] != -1 && s != -1) {
			int t = i;
			ans = ans * calc(t - s, a[s - 1], a[t]) % mod;
			s = -1;
		}
	}
	if (s != -1) ans = ans * calc(n + 1 - s, a[s - 1], a[n + 1]) % mod;
	return ans;
}

signed main() {
	cin >> t >> k;
	for (int i = 1, x; i <= t; i++) {
		cin >> x;
		if (i & 1) {
			a[++n] = x;
			if (n >= 2 && x != -1 && a[n - 1] != -1 && x == a[n - 1]) return (puts("0"), 0);
		} else {
			b[++m] = x;
			if (m >= 2 && x != -1 && b[m - 1] != -1 && x == b[m - 1]) return (puts("0"), 0);
		}
	} 
	p[0] = 1;
	for (int i = 1; i <= t; i++) p[i] = p[i - 1] * (k - 1) % mod;
	invk = power(k, mod - 2);
	cout << solve(a, n) * solve(b, m) % mod << endl;
	return 0;
}
2023/8/3 15:44
加载中...