zoukankan      html  css  js  c++  java
  • AT2022 [ARC059D] バイナリハック / Unhappy Hacking

    AT2022 [ARC059D] バイナリハック / Unhappy Hacking

    题意:给长度(n <= 5000)和一个长度(len <= 5000)(01)串,要求用键盘(0,1)和回退键来输入,正好花费(n)次恰好输入成(s)串,求方案数。
    题解:方案数量大概率是(dp),设(dp)数组(dp_{i,j})表示的是操作(i)次字串长度为(j)的方案数,(无论是啥串,至于为啥先往下看),那么就有两种情况,一种是打(01),还有一种是回退键。

    • 若是输入(01),那么必然(dp[i][j])就是(dp[i-1][j-1])转化来的,那么可以输入(01)两种选择,所以应当是(dp[i + 1][j + 1] = dp[i][j] imes 2).
    • 若是回退键,那么必然(dp[i][j])就是(dp[i-1][j+1])转化来的.
      代码:
    #include <algorithm>
    #include <cmath>
    #include <cstdio>
    #include <cstring>
    #include <iostream>
    #include <map>
    #include <queue>
    #include <vector>
    #include <set>
    
    using namespace std;
    typedef long long ll;
    const int N = 5009;
    map<ll, ll>ma;
    vector<ll>vec;
    const ll mod = 1e9 + 7;
    ll dp[N][N];
    ll q_pow(ll a, ll k) {
        ll ret = 1;
        ll x = a;
        while (k) {
            if (k & 1) {
                (ret *= x) %= mod;
            }
            k >>= 1;
            (x *= x) %= mod;
        }
        return ret;
    }
    ll inv(ll a, ll mod) {
        return (q_pow(a, mod-2)%mod + mod) % mod;
    }
    void solve() {
        int n;cin >> n;
        string s;cin >> s;
        int len = s.size();
        dp[0][0] = 1;
        for (int i = 0; i <= n; i++) {
            for (int j = 0; j <= i; j++) {
                (dp[i + 1][j + 1] += dp[i][j] * 2 % mod)%=mod;
                (dp[i + 1][max(0, j-1)] += dp[i][j]) %= mod;
            }
        }
        //cout << dp[n][len] << endl;
        //cout << q_pow(2, 1) << endl;
        cout << dp[n][len]  * inv(q_pow(2, len), mod)%mod << endl;
    }
    signed main() {
        ll t = 1;
        //cin >> t;
        while (t--) {
            solve();
        }
    }
    
  • 相关阅读:
    图像滤波
    直方图histeq
    直方图
    基于灰度变换的图像增强
    图像增强
    图像旋转和缩放
    图像点运算
    像素的连接与联通
    程序员进阶之算法练习(一)
    RxSwift 系列(二)
  • 原文地址:https://www.cnblogs.com/Xiao-yan/p/14488179.html
Copyright © 2011-2022 走看看