Educational Codeforces Round 174 (Rated for Div. 2) C题题解记录

如果以下条件成立,我们就把一个整数序列称为美丽

  • 它的长度至少为 3 ;
  • 除第一个元素外,每个元素的左边都有一个比它小的元素;
  • 除最后一个元素外,每个元素的右边都有一个比它大的元素;
    回顾一下,子序列是指在不改变其余元素顺序的情况下,通过删除某些元素而从另一个序列中得到的序列。
    给你一个大小为 n 的整数数组 a ,其中 每个元素都从 1 到 3。你的任务是计算数组 a 中优美子序列的个数。由于答案可能很大,请打印出它的模数 998244353。

解:

由题:可行的方案必须是类似1 2 2 2 2 … 3这种的。1开头,3结尾,中间有非零0个2。
每次输入一个新的数的时候,如果这个数是2,那么假设前面有a个1,此时这个2可以接到前面a个1的后面。假设b为此时前面形如1 2 2 2…的序列的个数,那么同时此位置的2也可以接到前面b个后面。例如1 2 2,此时a=1,b=3。当再次遇到2的时候,组成1 2(q) 2(w) 2(x),此时b的个数为x接到前面a个1的后面这种可能加原先b种可能以及,先前1 q,1 w,1 q w的后面。故遇到2的时候,b=b*2+a。
遇到3的时候,可以直接接到前面b种可能的后面即可。

#include <bits/stdc++.h>

using namespace std;
#define int long long
#define uint unsigned int
#define pii pair<int,int>
const int mod = 998244353;
int dx[] = {1, 0, -1, 0};
int dy[] = {0, 1, 0, -1};


void solve() {

    int n;
    cin >> n;
    vector<int> arr(n + 1);
    int a = 0, b = 0;
    int ans = 0;
    for (int i = 1; i <= n; i++) {
        cin >> arr[i];


        if (arr[i]==1) a++;
        else if (arr[i]==2){
            b=(b*2%mod+a)%mod;
        }else ans=(ans+b)%mod;
    }

    cout<<ans<<endl;





}

signed main() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    int T = 1;
    cin >> T;
    while (T--) {
        solve();
    }
    return 0;
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值