Codeforces Round #604 (Div. 2) D、E、F题解

Beautiful Sequence

\[
Time Limit: 1000 ms\quad Memory Limit: 256 MB
\]
首先我们可以考虑到 \(0\) 只能 和 \(1\) 放在一起、\(3\) 只能和 \(2\) 放在一起,那么我们想办法先把 \(0\) 和 \(3\) 凑出来,最后就剩下 \(1\) 和 \(2\) 了,我们只要把他们放在一起就可以了。
所以我们可以贪心考虑三个 \(string\),分别长成 \(0101...0101\)、\(2323...2323\)、\(1212...1212\) 这样的,那么现在的问题就是把这三个 \(string\) 合并起来,那么完全可以把他们全排列并二进制枚举每个 \(string\) 是否翻转,然后 \(check\) 一遍。

view

#include <map>
#include <set>
#include <list>
#include <ctime>
#include <cmath>
#include <stack>
#include <queue>
#include <cfloat>
#include <string>
#include <vector>
#include <cstdio>
#include <bitset>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
#define  lowbit(x)  x & (-x)
#define  mes(a, b)  memset(a, b, sizeof a)
#define  fi         first
#define  se         second
#define  pb         push_back
#define  pii        pair<int, int>
#define  INOPEN     freopen("in.txt", "r", stdin)
#define  OUTOPEN    freopen("out.txt", "w", stdout)

typedef unsigned long long int ull;
typedef long long int ll;
const int    maxn = 2e5 + 10;
const int    maxm = 1e5 + 10;
const ll     mod  = 1e9 + 7;
const ll     INF  = 1e18 + 100;
const int    inf  = 0x3f3f3f3f;
const double pi   = acos(-1.0);
const double eps  = 1e-8;
using namespace std;

int n, m;
int cas, tol, T;
int a, b, c, d;

string s[4], ss;

bool ok(string a, string b, string c) {
    int lena = a.size(), lenb = b.size(), lenc = c.size();
    int len = lena+lenb+lenc;
    for(int i=0; i<7; i++) {
        if(i&(1<<(0))) {
            reverse(a.begin(), a.end());
        }
        if(i&(1<<(1))) {
            reverse(b.begin(), b.end());
        }
        if(i&(1<<(2))) {
            reverse(c.begin(), c.end());
        }
        ss = a+b+c;
        if(i&(1<<(0))) {
            reverse(a.begin(), a.end());
        }
        if(i&(1<<(1))) {
            reverse(b.begin(), b.end());
        }
        if(i&(1<<(2))) {
            reverse(c.begin(), c.end());
        }

        int flag = 1;
        for(int i=1; i<len; i++) {
            if(abs(ss[i]-ss[i-1])!=1) {
                flag = 0;
                break;
            }
        }
        if(flag) {
            printf("YES\n");
            for(int i=0; i<len; i++) {
                printf("%c%c", ss[i], i==len-1 ? '\n':' ');
            }
            return true;
        }
    }
    return false;
}

int main() {
    scanf("%d%d%d%d", &a, &b, &c, &d);
    s[1] = "";
    while(a&&b) {
        s[1] += "01";
        a--, b--;
    }
    if(a) {
        s[1] += "0";
        a--;
    }
    if(b) {
        s[1] = "1"+s[1];
        b--;
    }

    s[3] = "";
    while(c&&d) {
        s[3] += "23";
        c--, d--;
    }
    if(c) {
        s[3] += "2";
        c--;
    }
    if(d) {
        s[3] = "3"+s[3];
        d--;
    }

    s[2] = "";
    while(b&&c) {
        s[2] += "12";
        b--, c--;
    }
    if(b) {
        s[2] += "1";
        b--;
    }
    if(c) {
        s[2] = "2"+s[2];
        c--;
    }
    if(a||b||c||d)  return 0*puts("NO");
    do {
        if(ok(s[1], s[2], s[3]))
            return 0;
    } while(next_permutation(s+1, s+1+3));
    puts("NO");
    return 0;
}

Beautiful Mirrors

\[
Time Limit: 2000 ms\quad Memory Limit: 256 MB
\]
首先令 \(dp[i]\) 表示从第 \(i\) 天到结束所需要的期望天数,为了方便,可以假设 \(n+1\) 天为结束位置,那么 \(dp[n+1] = 0\)。
对于 \(1<=i<=n\),有 \(dp[i] = \frac{p_i*dp[i+1] + (100-p_i)*dp[1]}{100}+1\)
然后一直带进去,最后可以发现 \(dp[1]\) 可以表示为
\[
dp[1] = A*dp[1] + B + 1
\]
其中 \(A、B\) 都是具体的数字,那么就得到的 \(dp[1]\) 的值。

view

#include <map>
#include <set>
#include <list>
#include <ctime>
#include <cmath>
#include <stack>
#include <queue>
#include <cfloat>
#include <string>
#include <vector>
#include <cstdio>
#include <bitset>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
#define  lowbit(x)  x & (-x)
#define  mes(a, b)  memset(a, b, sizeof a)
#define  fi         first
#define  se         second
#define  pb         push_back
#define  pii        pair<int, int>
#define  INOPEN     freopen("in.txt", "r", stdin)
#define  OUTOPEN    freopen("out.txt", "w", stdout)

typedef unsigned long long int ull;
typedef long long int ll;
const int    maxn = 2e5 + 10;
const int    maxm = 1e5 + 10;
const ll     mod  = 998244353;
const ll     INF  = 1e18 + 100;
const int    inf  = 0x3f3f3f3f;
const double pi   = acos(-1.0);
const double eps  = 1e-8;
using namespace std;

int n, m;
int cas, tol, T;

int p[maxn];

ll fpow(ll a, ll b) {
    ll ans = 1;
    while(b) {
        if(b&1) ans = ans*a%mod;
         a = a*a%mod;
         b >>= 1;
    }
    return ans;
}

int main() {
    ll M = fpow(100ll, mod-2);
    scanf("%d", &n);
    for(int i=1; i<=n; i++) {
        scanf("%d", &p[i]);
    }
    ll b = 0, c = 0;
    ll tmpb = 1;
    for(int i=1; i<=n; i++) {
        b += tmpb*(100ll-p[i])%mod*M%mod;
        c += tmpb;
        tmpb *= p[i]*M%mod;
        b %= mod, c %=mod, tmpb %= mod;
    }
    b = mod-b+1;
    b = (b%mod+mod)%mod;
    ll ans = c*fpow(b, mod-2)%mod;
    printf("%lld\n", ans);
    return 0;
}

Beautiful Bracket Sequence (easy version)

\[
Time Limit: 2000 ms\quad Memory Limit: 256 MB
\]
令 \(dp[i][j]\) 表示从 \(i\) 到 \(j\) 区间内,所有情况的括号最深深度之和。
那么转移的时候 \(dp[i][i] = 0\),\(dp[i][i+1]\) 为 \(s[i]\) 和 \(s[i+1]\) 能否组成 \(()\)。

对于更大的区间,只需要考虑最左和最右端点就可以。

  1. 如果\(s[i]\) 可以放成 \((\)

    • 如果 \(s[j]\) 可以放成 \((\),\(dp[i][j] += dp[i][j-1]\)
    • 如果 \(s[j]\) 可以放成 \()\),\(dp[i][j] += dp[i+1][j-1] + 2^k\),\(k\) 代表 \([i+1,j-1]\) 这段内 \(?\) 的个数。
  2. 如果 \(s[i]\) 可以放成 \()\)
    • 如果 \(s[j]\) 可以放成 \((\),\(dp[i][j] += dp[i+1][j-1]\)
    • 如果 \(s[j]\) 可以放成 \()\),\(dp[i][j] += dp[i+1][j]\)

然后有一部分会被重复计算,也就是 \(dp[i+1][j-1]\) 这一段,所以只要顺便记录一下转移过程中计算了几次这一段,然后扣掉多计算的就可以了。

view

#include <map>
#include <set>
#include <list>
#include <ctime>
#include <cmath>
#include <stack>
#include <queue>
#include <cfloat>
#include <string>
#include <vector>
#include <cstdio>
#include <bitset>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
#define  lowbit(x)  x & (-x)
#define  mes(a, b)  memset(a, b, sizeof a)
#define  fi         first
#define  se         second
#define  pb         push_back
#define  pii        pair<int, int>
#define  INOPEN     freopen("in.txt", "r", stdin)
#define  OUTOPEN    freopen("out.txt", "w", stdout)

typedef unsigned long long int ull;
typedef long long int ll;
const int    maxn = 2e3 + 10;
const int    maxm = 1e5 + 10;
const ll     mod  = 998244353;
const ll     INF  = 1e18 + 100;
const int    inf  = 0x3f3f3f3f;
const double pi   = acos(-1.0);
const double eps  = 1e-8;
using namespace std;

int n, m, TT;
int cas, tol;

int a[maxn] = {0};
char s[maxn];
ll dp[maxn][maxn];

ll fpow(ll a, ll b) {
    ll ans = 1;
    while(b) {
        if(b&1) ans = ans*a%mod;
        a = a*a%mod;
        b >>= 1;
    }
    return ans;
}

int main() {
    scanf("%s", s+1);
    n = strlen(s+1);
    for(int i=1; i<=n; i++) {
        a[i] = a[i-1]+(s[i]=='?');
        dp[i][i] = 0;
        dp[i][i+1] = (i+1<=n && s[i]!=')' && s[i+1]!='(');
    }
    for(int d=3; d<=n; d++) {
        for(int i=1, j=d, c; j<=n; i++, j++) {
            dp[i][j] = 0, c = -1;
            if(s[i] != ')') {
                if(s[j] != ')') dp[i][j] += dp[i][j-1], c++;
                if(s[j] != '(') dp[i][j] += dp[i+1][j-1] + fpow(2, a[j-1]-a[i]);
            }
            if(s[i] != '(') {
                if(s[j] != ')') dp[i][j] += dp[i+1][j-1], c++;
                if(s[j] != '(') dp[i][j] += dp[i+1][j], c++;
            }
            dp[i][j] -= max(c, 0)*dp[i+1][j-1];
            dp[i][j] %= mod;
//          printf("dp[%d][%d] = %lld\n", i, j, dp[i][j]);
        }
    }
    printf("%lld\n", dp[1][n]);
    return 0;
}

原文地址:https://www.cnblogs.com/Jiaaaaaaaqi/p/12037553.html

时间: 2024-10-09 07:30:15

Codeforces Round #604 (Div. 2) D、E、F题解的相关文章

Codeforces Round #604 (Div. 2) 练习A,B题解

A题 链接 思路分析: 因为只需要做到相邻的不相同,利用三个不同的字母是肯定可以实现的, 所以直接先将所有的问号进行替换,比如比前一个大1,如果与后面的冲突,则再加一 代码(写的很烂): #include <bits/stdc++.h> using namespace std; int check( string a) { for (int i = 0; i < a.length(); ++i) { if (i==0) { if (a[i]==a[i+1]) { return 0; }

Codeforces Round #604 (Div. 2)

https://codeforces.com/contest/1265 这场的2E是1C的不带checkpoints的版本. B - Beautiful Numbers 题意:给一个数组是一个[1,n]的permutation.对每个m∈[1,n]问[1,m]是否连续存在在这个数组中. 题解: 首先,[1,1]一定存在. 然后向指定方向扩展到2,若经过2以外的数,把2标记为不存在. 3已经被扩展,或3在区间左右?是:否. 所以每次就问新的数是不是在已有区间中或者左右,是则包含,否则扩展到有为止.

Codeforces Round #604 (Div. 2) A. Beautiful String

链接: https://codeforces.com/contest/1265/problem/A 题意: A string is called beautiful if no two consecutive characters are equal. For example, "ababcb", "a" and "abab" are beautiful strings, while "aaaaaa", "abaa&

Codeforces Round #604 (Div. 2) D. Beautiful Sequence(构造)

链接: https://codeforces.com/contest/1265/problem/D 题意: An integer sequence is called beautiful if the difference between any two consecutive numbers is equal to 1. More formally, a sequence s1,s2,-,sn is beautiful if |si?si+1|=1 for all 1≤i≤n?1. Trans

Codeforces Round #604 (Div. 2) C. Beautiful Regional Contest

链接: https://codeforces.com/contest/1265/problem/C 题意: So the Beautiful Regional Contest (BeRC) has come to an end! n students took part in the contest. The final standings are already known: the participant in the i-th place solved pi problems. Since

Codeforces Round #604 (Div. 2)D(构造)

构造,枚举起点,如果一个序列成立,那么将它reverse依然成立,所以两个方向(从小到大或从大到小)没有区别,选定一个方向进行探测,直到探测不到以后回头,只要所给数据能成立,那么能探测进去就能探测出来,否则就不能构造. 1 #define HAVE_STRUCT_TIMESPEC 2 #include<bits/stdc++.h> 3 using namespace std; 4 int num[7]; 5 int sum; 6 int main(){ 7 ios::sync_with_std

Codeforces Round #604 (Div. 2)(A-E)

A. Beautiful String 题意:把'?'换成'a' or 'b' or 'c'使得相邻的两个字符不相同. 暴力枚举每个'?'前后. #include <bits/stdc++.h> using namespace std; const int MAXN=1e5+10; string s; int main(){ ios::sync_with_stdio(false); int T; cin>>T; while(T--){ cin>>s; bool ok=t

Codeforces Round #536 (Div. 2)

目录 Codeforces Round #536 (Div. 2) A 题目大意 题解 卡点 C++ Code: B 题目大意 题解 卡点 C++ Code: C 题目大意 题解 卡点 C++ Code: D 题目大意 题解 卡点 C++ Code: E 题目大意 题解 卡点 C++ Code: F 题目大意 题解 卡点 C++ Code: Codeforces Round #536 (Div. 2) A 题目大意 给你一个\(n\times n(n\leqslant500)\)的矩阵,只包含.

Codeforces Round #486 (Div. 3) F. Rain and Umbrellas

Codeforces Round #486 (Div. 3) F. Rain and Umbrellas 题目连接: http://codeforces.com/group/T0ITBvoeEx/contest/988/problem/E Description Polycarp lives on a coordinate line at the point x=0. He goes to his friend that lives at the point x=a. Polycarp can