题解:一开始做这个题的时候想过尺取法,但是因为没有逆元的知识,不知道该如何不断删除左端元素。其实这题并不难想,设l,r为两端开始都置为1,当长度小于k的时候不断乘右端元素并取余,当长度等于k时删除左端元素并且乘上右端端元素。注意:若右端元素为0时,就将两个端点都移到下一位从新开始。

#pragma GCC optimize(3,"Ofast","inline")
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <math.h>
#include <string>
#include <list>
#include <set>
#include <map>
#include <stack>
#include <algorithm>
#define maxn 110
#define MaxN 0x3f3f3f
#define MinN 0xc0c0c0
typedef long long ll;
using namespace std;
const int mod=998244353;
ll a[300010];

ll quickpow(ll a,ll b){
    ll ans=1;
    while(b){
        if(b%2==1)
        ans=ans*a%mod;
        a=a*a%mod;
        b=b/2;
    }
    return ans;
}
int main()
{
    int n,k;
    cin>>n>>k;
    for(int i=1;i<=n;i++)  scanf("%lld",&a[i]);
    ll l=1,r=1;
    ll imax=0;
    ll sum=1;
    while(r<=n){
        if(r-l<k-1&&a[r]!=0){
            sum=(sum*a[r])%mod;
            r++;
        }
        else if(r-l==k-1&&a[r]!=0){
            sum=(sum*a[r])%mod;
            imax=max(imax,sum);
            r++;
        }
        else if(r-l==k&&a[r]!=0){
            sum=(sum%mod*a[r]%mod*quickpow(a[l],mod-2))%mod;   //费马小定理不会的小伙伴可以去百度一下
            l++,r++;
            imax=max(imax,sum);
        }
        else if(a[r]==0){
            r++;
            l=r;
            sum=1;
        }
    }
    cout<<imax<<endl;
    return 0;
}

后续。。。
刚学会线段树就拿来写了一下这个题目
以上是逆元+尺取法,又现学了一下线段树用线段树莽一波也是不错的解法,本题线段树只涉及了插入和计算“和”的部分

#pragma GCC optimize(3,"Ofast","inline")
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <math.h>
#include <string>
#include <list>
#include <set>
#include <map>
#include <stack>
#include <algorithm>
#define maxn 1000000
#define MaxN 0x3f3f3f
#define MinN 0xc0c0c0
typedef long long ll;
using namespace std;
const int mod=998244353;
ll arr[maxn];
ll tree[maxn]={1};
void build_tree(ll node,ll start,ll ends){
    if(start==ends){
        tree[node]=arr[start];
    }
    else{
        ll mid=(start+ends)/2;
        ll left_node=2*node+1;
        ll right_node=2*node+2;
        build_tree(left_node,start,mid);
        build_tree(right_node,mid+1,ends);
        tree[node]=(tree[left_node]*tree[right_node])%mod;
    }
    return ;
}

ll query_tree(ll node,ll start,ll ends,ll l,ll r,ll sum){
    if(r<start||l>ends)  return 1;
    else if(l<=start&&r>=ends){
        return (tree[node]*sum)%mod;
    }
    else{
        ll mid=(start+ends)/2;
        ll left_node=2*node+1;
        ll right_node=2*node+2;
        ll sum_left=query_tree(left_node,start,mid,l,r,sum);
        ll sum_right=query_tree(right_node,mid+1,ends,l,r,sum);
        return ((sum_left*sum_right)*sum%mod)%mod;
    }
}
int main()
{
    int n,m,k;
    cin>>n>>k;
    for(int i=0;i<n;i++) scanf("%lld",&arr[i]);
    build_tree(0,0,n-1);
    //for(int i=0;i<100;i++) cout<<tree[i]<<" ";
    ll imax=0;
    for(int i=0;i+k-1<n;i++){
        ll ans;
        ans=query_tree(0,0,n-1,i,i+k-1,1);
        imax=max(imax,ans);
    }
    cout<<imax<<endl;
    return 0;
 
}