考场上想得太简单了
很显然,奇数位和偶数位上的分开后,相邻位置的数字不相同就是good了
然后考场上直接乘法原理了。。。
其实不然,因为1 -1 -1 1这种跟2 -1 -1 1这种答案是不相同的,但是我考场上没考虑到就把样例全过了。
所以需要讨论,奇数位偶数位分开后,单独对其中一条数列讨论,分为左右都没有限制,只有左边有限制,只有右边,两边都有但数字不同,两边都有单数字相同这5种情况,分别对每种情况求出所有长度的答案。
右边没有限制的很简单,直接每次*(k-1)就行了。
右边有限制,我们只需要考虑,每一位上,假如没有限制,总共有sum个情况,跟右边的限制相等的有cnt个情况
那么当前长度的答案就是sum-cnt,因为当前长度的最后一个不能等于右边的限制。
其余的类似这样的递推,左边的限制只影响最初的sum和cnt的大小。
#include<bits/stdc++.h>
#define maxl 200010
using namespace std;
const int mod=998244353;
int n,k,cnt1,cnt2;
long long ans;
int a[maxl],od[maxl],ev[maxl];
long long f00[maxl],f01[maxl],f10[maxl],f11s[maxl],f11d[maxl];
inline void prework()
{
scanf("%d%d",&n,&k);
for(int i=1;i<=n;i++)
{
scanf("%d",&a[i]);
if(i&1) od[++cnt1]=a[i];
else ev[++cnt2]=a[i];
}
f00[1]=k;
for(int i=2;i<=n;i++)
f00[i]=f00[i-1]*(k-1)%mod;
long long sum=k,cnt=1,t1,t2;
f01[1]=sum-cnt;
for(int i=2;i<=n;i++)
{
t1=sum*(k-1)%mod;
t2=((sum-cnt)%mod+mod)%mod;
f01[i]=((t1-t2)%mod+mod)%mod;
sum=t1;cnt=t2;
}
f10[1]=(k-1);
for(int i=2;i<=n;i++)
f10[i]=f10[i-1]*(k-1)%mod;
sum=k-1,cnt=0;
f11s[1]=k-1;
for(int i=2;i<=n;i++)
{
t1=sum*(k-1)%mod;
t2=((sum-cnt)%mod+mod)%mod;
f11s[i]=((t1-t2)%mod+mod)%mod;
sum=t1;cnt=t2;
}
sum=k-1,cnt=1;
f11d[1]=k-2;
for(int i=2;i<=n;i++)
{
t1=sum*(k-1)%mod;
t2=((sum-cnt)%mod+mod)%mod;
f11d[i]=((t1-t2)%mod+mod)%mod;
sum=t1;cnt=t2;
}
}
inline void mainwork()
{
ans=1;
for(int i=1;i<=n;i++)
if(a[i]>0)
{
if(i+2<=n && a[i+2]>0 && a[i+2]==a[i])
{
ans=0;
return;
}
}
int l=0,r=0;
while(l<=cnt1 && r<=cnt1)
{
do
l++;
while(od[l]!=-1 && l<=cnt1);
if(l>cnt1) break;
r=l;
while(od[r+1]==-1 && r<=cnt1)
r++;
if(l-1==0)
{
if(r==cnt1)
ans=ans*f00[cnt1]%mod;
else
ans=ans*f01[r-l+1]%mod;
}
else if(r==cnt1)
ans=ans*f10[r-l+1]%mod;
else
{
if(od[l-1]==od[r+1])
ans=ans*f11s[r-l+1]%mod;
else
ans=ans*f11d[r-l+1]%mod;
}
l=r+1;
}
l=0;r=0;
while(l<=cnt2 && r<=cnt2)
{
do
l++;
while(ev[l]!=-1 && l<=cnt2);
if(l>cnt2) break;
r=l;
while(ev[r+1]==-1 && r<=cnt2)
r++;
if(l-1==0)
{
if(r==cnt2)
ans=ans*f00[cnt2]%mod;
else
ans=ans*f01[r-l+1]%mod;
}
else if(r==cnt2)
ans=ans*f10[r-l+1]%mod;
else
{
if(ev[l-1]==ev[r+1])
ans=ans*f11s[r-l+1]%mod;
else
ans=ans*f11d[r-l+1]%mod;
}
l=r+1;
}
}
inline void print()
{
printf("%lld",ans);
}
int main()
{
prework();
mainwork();
print();
return 0;
}