• D. Magic Breeding


    题目链接:http://codeforces.com/contest/878/problem/D

    D. Magic Breeding
    time limit per test
    4 seconds
    memory limit per test
    1024 megabytes
    input
    standard input
    output
    standard output

    Nikita and Sasha play a computer game where you have to breed some magical creatures. Initially, they have k creatures numbered from 1to k. Creatures have n different characteristics.

    Sasha has a spell that allows to create a new creature from two given creatures. Each of its characteristics will be equal to the maximum of the corresponding characteristics of used creatures. Nikita has a similar spell, but in his spell, each characteristic of the new creature is equal to the minimum of the corresponding characteristics of used creatures. A new creature gets the smallest unused number.

    They use their spells and are interested in some characteristics of their new creatures. Help them find out these characteristics.

    Input

    The first line contains integers nk and q (1 ≤ n ≤ 105, 1 ≤ k ≤ 12, 1 ≤ q ≤ 105) — number of characteristics, creatures and queries.

    Next k lines describe original creatures. The line i contains n numbers ai1, ai2, ..., ain (1 ≤ aij ≤ 109) — characteristics of the i-th creature.

    Each of the next q lines contains a query. The i-th of these lines contains numbers tixi and yi (1 ≤ ti ≤ 3). They denote a query:

    • ti = 1 means that Sasha used his spell to the creatures xi and yi.
    • ti = 2 means that Nikita used his spell to the creatures xi and yi.
    • ti = 3 means that they want to know the yi-th characteristic of the xi-th creature. In this case 1 ≤ yi ≤ n.

    It's guaranteed that all creatures' numbers are valid, that means that they are created before any of the queries involving them.

    Output

    For each query with ti = 3 output the corresponding characteristic.

    Examples
    input
    Copy
    2 2 4
    1 2
    2 1
    1 1 2
    2 1 2
    3 3 1
    3 4 2
    output
    Copy
    2
    1
    input
    Copy
    5 3 8
    1 2 3 4 5
    5 1 2 3 4
    4 5 1 2 3
    1 1 2
    1 2 3
    2 4 5
    3 6 1
    3 6 2
    3 6 3
    3 6 4
    3 6 5
    output
    Copy
    5
    2
    2
    3
    4
    Note

    In the first sample, Sasha makes a creature with number 3 and characteristics (2, 2). Nikita makes a creature with number 4 and characteristics (1, 1). After that they find out the first characteristic for the creature 3 and the second characteristic for the creature 4.

    一开始的时候,给你k个怪兽,每个怪兽有n个属性。
    然后现在你有三个操作:
    第一个操作是用x和y怪物生成一个新的怪物,这个怪物的属性是x和y的最大值
    第二个操作是用x和y怪物生成一个新的怪物,这个怪物的属性是x和y的最小值
    第三个操作是询问第x个怪物的第y个属性是多少。

    思路:先看一下简单情况,假如属性只有0和1的情况,那么取大的是不是就是或操作呢‘? 取小的是不是就是与操作呢?  显然是的

    但是你可能会说 问题是属性值不是1和0啊   是的,我也这么想。 怎么用0和1表示出来呢? 想想,是不是不管你怎么操作,最后出来的答案一定是原本有的怪兽演变过来的?

    想到这就好点了,那么也就是说,加入我们可以知道新得到的怪兽是通过哪几个怪兽演变过来的就好了。 

    状态压缩,最多有12种怪兽,所以最多的情况是1<<12种情况,我们把首先每种怪兽可能属于的情况存起来  比如怪兽1  那么它可能属于的情况就是  ***********中第一位为1  其它随便怎么

    组合。  这样存起来之后,每种怪兽刚开始可能的情况就存起来了  接下来是操作,假如是操作1  那么还是或操作   假如是操作2  那么还是与操作

    假如是操作3  我们先把属性和对应的下标存起来  按照属性值排序   得到的第一个满足条件的值就是答案了。

    代码:

    #include<iostream>
    #include<cstdio>
    #include<bitset>
    #include<vector>
    #include<algorithm>
    using namespace std;
    typedef long long LL;
    const int maxn=1e5+10;
    const LL mod=998244353;
    int a[15][maxn];
    
    bitset<4096> s[maxn];//1<<12=4096
    int main()
    {
        int N,M,Q;
        scanf("%d%d%d",&N,&M,&Q);
        for(int i=1;i<=M;i++)
        {
            for(int j=1;j<=N;j++)
            {
                scanf("%d",&a[i][j]);
            }
        }
    //    for(int i=1;i<=M;i++)
    //    {
    //        for(int j=1;j<=N;j++)
    //        {
    //            cout<<a[i][j]<<" ";
    //        }
    //        cout<<endl;
    //    }
        for(int i=1;i<4096;i++)
        {
            for(int j=1;j<=M;j++)
            {
                if(i&(1<<(j-1))) s[j].set(i);
            }
        }
    //    for(int i=1;i<=M;i++) cout<<s[i]<<endl;
        int tot=M+1;
        for(int i=1;i<=Q;i++)
        {
            int t,x,y;
            scanf("%d%d%d",&t,&x,&y);
            if(t==1) s[tot++]=s[x]|s[y];
            else if(t==2) s[tot++]=s[x]&s[y];
            else
            {
                vector<pair<int,int> >v;
                for(int j=1;j<=M;j++) v.push_back({a[j][y],j});
                sort(v.begin(),v.end(),greater<pair<int,int> >());
    //            for(int j=0;j<M;j++) cout<<v[j].first<<" "<<v[j].second<<endl;
                int b=0;
                for(int j=0;j<M;j++)
                {
                    b|=(1<<(v[j].second-1));
    //                cout<<"b:"<<b<<endl;
                    if(s[x][b])
                    {
                        printf("%d
    ",a[v[j].second][y]);
                        break;
                    }
                }
            }
        }
        return 0;
    }
    当初的梦想实现了吗,事到如今只好放弃吗~
  • 相关阅读:
    包图网+千图网图片代下
    Java基于二维数组自定义的map
    java23种设计模式-行为型模式-中介者模式
    基于SpringBoot、Redis和RabbitMq的商品秒杀处理
    wps+稻壳vip账号免费分享
    wps+稻壳vip15天领取地址
    图精灵、易图、笔图,vip免费分享
    文库、氢元素、办图、六图,vip免费分享
    快图网、千库,go设计,vip免费分享
    MySQL索引规范及优化
  • 原文地址:https://www.cnblogs.com/caijiaming/p/10859185.html
Copyright © 2020-2023  润新知