• 无题十三


    题解:

    第一题:异或的老套路,按位算贡献,统计某一位有多少个数为1,就用数位DP好了;

    #include<bits/stdc++.h>
    using namespace std;
    const int M = 1e6;
    #define ll long long 
    const ll mod = 1e9 + 7;
    int L, R, dp[35][2];
    int bin[33], cnt[33], digit[33];
    inline ll moc(ll a){return a >= mod ? a - mod : a;}
    void solve1(){
        ll ans = 0;
        for(int i = L; i <= R; i++)
            for(int j = L; j <= R; j++)
                ans = moc(ans + (i ^ j) % mod);
        printf("%lld
    ", ans);
    }
    
    int dfs(int dep, int s, bool f, int sum){
        if(!dep) return sum;
        if(!f && dp[dep][sum] != -1) return dp[dep][sum];
        int i = f ? digit[dep] : 1;
        int tmp = 0;
        for(; i >= 0; i--){
            if(dep == s && i) tmp += dfs(dep - 1, s, f & (i == digit[dep]), sum + 1);
            else tmp += dfs(dep - 1, s, f & (i == digit[dep]), sum);
        }
        if(f) return tmp;
        return dp[dep][sum] = tmp;
    }
    
    void get(int x, ll f){
        int d = 0;
        if(x < 0) return;
        while(x){
            digit[++d] = x & 1;
            x >>= 1;
        }
        for(int i = 1; i <= 31; i++){
            memset(dp, -1, sizeof(dp));
            cnt[i] += f * dfs(d, i, 1, 0); 
        }
    }
    
    void solve3(){
        memset(cnt, 0, sizeof(cnt));
        get(L-1, -1);
        get(R, 1);
        ll ans = 0;
        ll cc = R - L + 1;
        for(int j = 1; j <= 31; j++) ans = moc(ans + 1LL*bin[j] * cnt[j] % mod * (cc - cnt[j]) * 2 % mod);
        printf("%lld
    ", ans);
        
    }
    
    int main(){
        freopen("xor.in","r",stdin);
        freopen("xor.out","w",stdout);
        int T;
        scanf("%d", &T);
        bin[1] = 1;
        for(int i = 2; i <= 31; i++) bin[i] = bin[i-1] << 1;
        while(T--){
            scanf("%d%d", &L, &R);
            solve3();
        }
    }
    View Code

    第二题:博弈论;

    两堆石子:

     

    上面的表总结一下就是:我们知道(x, y)是必输状态,那么(x, z) z != y一定是必赢状态;

    分类讨论: z>y,我一定可以一步转移到(x,y) ; z<y, 如果(x,z)必输,那么(x,y)就可以转移到他,成为必赢状态,与已知条件矛盾;

    所以一个x,对应一个y, y‘'-x''的值相同时时,都是必赢状态;

    我们推广到三个状态:

    我们枚举每次选几个;

    (x, y, z)是已知必输状态;

    一次选两堆,如果x和原来相同,那么y''-z'' = y-z,一定是必赢状态,所以一堆确定时,令两堆差值和原来一样,我们就可以把他筛掉;

    一次选一堆,这是确定x,y,我们就可以把z''转化为z,我们就只需要看f(x,y)这个状态是否为z;

    一次选三堆,同时前去一个数达到(x,y,z),他就必赢,要求就是三个数之间的相差值同;

    我们从小往大枚举,不断筛数,没有被筛掉的他就必败,这样复杂度N^3

    #include<bits/stdc++.h>
    using namespace std;
    bool dp[305][305][305], mp[305][305][3];
    int a[4];
    void init(){
        for(int i = 0; i <= 300; i++)
            for(int j = 0; j <= i; j++)
                for(int k = 0; k <= j; k++){
                    bool ok = 1;
                    if(mp[i][j-k][0])ok=0;
                    if(mp[j][i-k][0])ok=0;
                    if(mp[k][i-j][0])ok=0;
                    if(mp[i][j][1])ok=0;
                    if(mp[i][k][1])ok=0;
                    if(mp[j][k][1])ok=0;
                    if(mp[i-j][j-k][2])ok=0;
                    if(ok){
                        dp[i][j][k]=1;
                        mp[i][j-k][0] = mp[j][i-k][0] = mp[k][i-j][0] = mp[i][j][1] = mp[i][k][1] = mp[j][k][1] = mp[i-j][j-k][2] = 1;
                    }
                }
    }
    
    int main(){
        freopen("stone.in","r",stdin);
        freopen("stone.out","w",stdout);
        int T;
        scanf("%d", &T);
        init();
        while(T--){
            int x, y, z;
            scanf("%d%d%d", &a[0], &a[1], &a[2]);
            sort(a, a+3);
            if(dp[a[2]][a[1]][a[0]])puts("No");
            else puts("Yes");
        }
    }
    View Code

    第三题:神奇的DP定义;

     以上可以2,0,-2序列可以自己手动画画证明;

    第一个优化:除了两端中间都可以随便取;

     我们已经证明了中间的系数是+2,-2,0,且两个2之间有一个-2,我们如果加上一段数,他大于0就往2中何必,小于0就往-2中合并,或者合并到0中,对答案只增不减;

    dp[i][j][k]表示处理到第i个数,分成了j段,处于k阶段

    阶段定义:0:处于系数为2

         1:处于2后面的0

         2:处于系数为-2

         3:处于-2后的0

    对于,我们可以和前面一起dp[i-1][j][0],可以自成一段,dp[i-1][j-1][3/2],就这样转移好了;

    对于两端的系数特殊变成1、-1,中间枚举转移;

    初值dp[i][0][1/3] = 0, 其余为-inf,表示开头可以随便从一个地方开始;

    答案在dp[i ( i > K) ][K] [0 / 2] 中取max,表示我可以在任意地方结束;

    #include<bits/stdc++.h>
    using namespace std;
    const int M = 4*1e4 + 5;
    int read(){
        int x=0,f=1;char c=getchar();
        while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
        while(c>='0'&&c<='9'){x=x*10+c-'0';c=getchar();}
        return x*=f;    
    }
    int dp[M][205][4], a[M];
    
    int main(){
        freopen("optimization.in","r",stdin);
        freopen("optimization.out","w",stdout);
        int n, k;
        scanf("%d%d", &n, &k);
        for(int i = 0; i <= n; i++)
            for(int j = 0; j <= k; j++)
                for(int z = 0; z < 4; z++) dp[i][j][z] = -1e9;
        for(int i = 0; i <= n; i++) dp[i][0][1] = dp[i][0][3] = 0;
        for(int i = 1; i <= n; i++){
            a[i] = read();
            for(int j = 1; j <= k; j++){
                int xs = 2 - (j == 1 || j == k);
                dp[i][j][0] = max(dp[i-1][j][0], max(dp[i-1][j-1][3], dp[i-1][j-1][2])) + xs * a[i];
                dp[i][j][1] = max(dp[i-1][j][1], dp[i-1][j-1][0]);
                dp[i][j][2] = max(dp[i-1][j][2], max(dp[i-1][j-1][0], dp[i-1][j-1][1])) - xs * a[i];
                dp[i][j][3] = max(dp[i-1][j][3], dp[i-1][j-1][2]);
                if(j != 1){
                    dp[i][j][1] = max(dp[i-1][j-1][1], dp[i][j][1]);
                    dp[i][j][3] = max(dp[i-1][j-1][3], dp[i][j][3]);
                }
            }
        } 
        int ans = -1e9;
        for(int i = 1; i <= n; i++)
            for(int j = 1; j <= k; j++) ans = max(dp[i][k][0], max(dp[i][k][2], ans));
        printf("%d
    ", ans);
    }
    View Code
  • 相关阅读:
    kubernetes HA 脚本
    架构之数据库分表分库
    架构之高可用性(HA)集群(Keepalived)
    架构之Nginx(负载均衡/反向代理)
    架构之消息队列
    oracle数据迁移
    Oracle中关于清除数据和释放表空间
    疑难杂症:org.hibernate.MappingException: Unknown entity,annotation配置Entity类报错
    j疑难杂症:java.lang.VerifyError: class org.hibernate.type.WrappedMaterializedBlobType overrides final method getReturnedClass.()Ljava/lang/Class;
    疑难杂症:java.lang.AbstractMethodError: org.apache.xerces.dom.DocumentImpl.setXmlVersion(Ljava/lang/String;)V
  • 原文地址:https://www.cnblogs.com/EdSheeran/p/9805277.html
Copyright © 2020-2023  润新知