• 四连测Day3


    三连爆炸

    极端快乐

    T1

    判断一个无向图能不能一笔画

    小学奥数 记得判图连不连通

    #include<bits/stdc++.h>
    using namespace std;
    inline int read()
    {
        int x = 0,f = 1;char ch = getchar();
        for(;!isdigit(ch);ch = getchar())if(ch == '-')f = -f;
        for(;isdigit(ch);ch = getchar())x = 10 * x + ch - '0';
        return x * f;
    }
    const int maxn = 1e5 + 10;
    int n,m,ind[maxn];
    int fa[maxn];
    inline int getfa(int x){return x == fa[x] ? x : fa[x] = getfa(fa[x]);}
    int main()
    {
        freopen("euler.in","r",stdin);
        freopen("euler.out","w",stdout);
        int T = read();
        while(T--)
        {
            int cntj = 0;memset(ind,0,sizeof(ind));
            n = read();m = read();
            for(int i=1;i<=n;i++)fa[i] = i;
            for(int i=1;i<=m;i++)
            {
                int u = read(),v = read();
                ind[u]++;ind[v]++;
                fa[getfa(u)] = getfa(v);
            }
            int flag = 0;
            for(int i=1;i<=n;i++)if(getfa(i) != getfa(1)){puts("NO");flag = 1;break;}
            if(flag)continue;
            for(int i=1;i<=n;i++)if(ind[i] & 1)cntj++;
            if(cntj == 0 || cntj == 2)cout<<"YES
    ";
            else puts("NO");
        }
    }
    View Code

    T2

    现在每个人都有1/2的概率当场去世

    现在有m条愿望,每条愿望是一个名单里的人不会当场去世

    求正好满足i条愿望的概率

    愿望条数<=5

    #include<bits/stdc++.h>
    #define int long long
    using namespace std;
    inline int read()
    {
        int x = 0,f = 1;char ch = getchar();
        for(;!isdigit(ch);ch = getchar())if(ch == '-')f = -f;
        for(;isdigit(ch);ch = getchar())x = 10 * x + ch - '0';
        return x * f;
    }
    const int maxn = 1e5 + 10,mod = 998244353,inv2 = 499122177;
    inline int ksm(int x,int k)
    {
        int ans = 1;
        while(k)
        {
            if(k & 1)ans = (ans * x) % mod;
            x = (x * x) % mod;
            k = k >> 1;
        }
        return ans;
    }
    int n,m;
    int wi[maxn][10];
    int dp[(1 << 5) + 5][maxn];
    inline int inv(int x){return ksm(x,mod - 2);}
    inline int div2(int x){return (x * inv2) % mod;}
    inline int cnt(int x)
    {
        int ret = 0;
        for(int i=0;i<=n;i++)
            if(x & (1 << i))ret++;
        return ret;
    }
    signed main()
    {
        freopen("avengers3.in","r",stdin);
        freopen("avengers3.out","w",stdout);
        n = read(),m = read();int MAXSTATE = (1 << n) - 1;
        for(int i=1;i<=n;i++)
        {
            int k = read();
            for(int j=1;j<=k;j++)
            {
                int u = read();
                wi[u][i] = 1;
            }
        }dp[MAXSTATE][0] = 1;
        for(int i=0;i<m;i++)
            for(int S=MAXSTATE;S>=0;S--)
            {
                if(!dp[S][i]) continue;
                (dp[S][i + 1] += (dp[S][i] * inv2) % mod) %= mod;
                int TS = S;for(int j=1;j<=n;j++)if(wi[i + 1][j] && ((1 << (j - 1)) & S))TS -= (1 << (j - 1));
                (dp[TS][i+1] += (dp[S][i] * inv2) % mod) %= mod;
            }
        int ans[10];memset(ans,0,sizeof(ans));
        for(int S=0;S<=MAXSTATE;S++)(ans[cnt(S)] += dp[S][m]) %= mod;
        for(int i=0;i<=n;i++)cout<<ans[i]<<" ";
    }
    View Code

    状压dp

    dp[i][S]表示前i个人,有可能满足S中愿望的概率

    1.dp[0][MAXS] = 1

    2.dp[i + 1][S] += (dp[i][S] / 2)(i + 1没有去世)

    3.dp[i + 1][S & TS] += (dp[i][S] / 2)(i + 1当场去世 TS为不包含i +1的愿望的集合)

    T3 询问一个长度为n的字符串中有多少个不包含s

    GT考试了解一下

    #include<bits/stdc++.h>
    #define int long long
    using namespace std;
    inline int read()
    {
        int x = 0,f = 1;char ch = getchar();
        for(;!isdigit(ch);ch = getchar())if(ch == '-')f = -f;
        for(;isdigit(ch);ch = getchar())x = 10 * x + ch - '0';
        return x * f;
    }
    const int maxn = 55;
    int tlen,mlen;
    string n;
    char str1[maxn],P[maxn];
    int f[maxn];const int mod = 998244353;
    string div(string a,int b)
    {
        string r,ans;
        int d=0;
        if(a=="0") return a;
        for(int i=0;i<a.size();i++)
        {
            r+=(d*10+a[i]-'0')/b+'0';
            d=(d*10+(a[i]-'0'))%b;
        }
        int p=0;
        for(int i=0;i<r.size();i++)
        if(r[i]!='0') {p=i;break;}
        return r.substr(p);
    }
    struct Matrix 
    {
        int n,m,a[maxn][maxn];
        Matrix() 
        {
            memset(a, 0, sizeof(a));
            n = m = mlen;
            for(int i = 0; i < n; i++) a[i][i] = 1;
        }
        void clear() 
        {
            n = m = 0;
            memset(a, 0, sizeof(a));
        }
        Matrix operator * (const Matrix& b) const 
        {
            Matrix t;
            t.clear();
            t.n = n; t.m = b.m;
            for(int i = 0; i < n; i++) 
                for(int j = 0; j < m; j++) 
                    for(int k = 0; k < m; k++) (t.a[i][j] += a[i][k] * b.a[k][j]) %= mod;
            return t;
        }
        Matrix operator ^ (string k) 
        {
            Matrix ans,t = *this;int len;
            while(1) 
            {
                len = k.length();
                if((k[len - 1] - '0') & 1)ans = ans * t;
                t = t * t;
                k = div(k,2);
                if(k == "0")break;
            }
            return ans;
        }
    }; 
    void getFail() 
    {
        int m = strlen(P);
        f[0] = 0; f[1] = 0;
        for(int i = 1; i < m; i++)
        {
            int j = f[i];
            while(j && P[i]!=P[j]) j = f[j];
            f[i+1] = P[i]==P[j] ? j+1 : 0;
        }
    }
    signed main() 
    {    
        freopen("string.in","r",stdin);
        freopen("string.out","w",stdout);
        cin>>n>>P;
        for(int i=0;i<26;i++)str1[i] = 'a' + i;
        tlen = strlen(str1), mlen = strlen(P);
        getFail();
        Matrix ans;
        ans.clear();
        ans.n = ans.m = mlen;
        for(int i = 0; i < mlen; i++) 
        {
            for(int j = 0; j < tlen; j++) 
            {
                int t = i;
                while(t && P[t]!=str1[j]) t = f[t];
                if(P[t] == str1[j])  t++;
                ans.a[i][t]++;
            }
        }
        ans = ans ^ n;
        int ret = 0;
        for(int i = 0; i < mlen; i++) (ret += ans.a[0][i]) %= mod;
        cout<<ret;
        return 0;
    }
    View Code
  • 相关阅读:
    [BZOJ1620][Usaco2008 Nov]Time Management 时间管理
    [BZOJ1634][Usaco2007 Jan]Protecting the Flowers 护花
    [BZOJ1725][Usaco2006 Nov]Corn Fields牧场的安排
    [BZOJ1708][Usaco2007 Oct]Money奶牛的硬币
    [BZOJ1690][Usaco2007 Dec]奶牛的旅行
    fzu 2132 LQX的作业
    fzu 2139 久违的月赛之二
    poj 1849 Two 树形dp
    师范大学 e: skyscrapers
    O(∩_∩)O~~
  • 原文地址:https://www.cnblogs.com/Kong-Ruo/p/9448415.html
Copyright © 2020-2023  润新知