zoukankan      html  css  js  c++  java
  • UVA12096 The SetStack Computer

    UVA12096The SetStack Computer

    需要对每个集合用一个ID来代替,方便在栈中模拟,毕竟操作最多10000个,意味着ID最多只有10000个。

    然后要做set和ID(int型)之间的双映射,也就是操作时从栈中取出ID,开一个vector<set<int> >,下标对应集合ID,每一个都是一个集合,里面有他包含的集合元素的ID;入栈时需要把操作得到的集合找出其ID,若没有则开一个新的。

    所以就是map<set<int>,int>实现。(开拓眼界了。。)

    查找的复杂度$O(玄学)$

    还有就是才知道有这样几个函数可以帮助实现集合的并集、交集,比我手写的快多了,还很方便。除了可以用在set上,好像vector也可以。。

    set_union(a.begin(),a.end(),b.begin(),b.end(),inserter(c,c.begin()));(并集)
    set_intersection(a.begin(),a.end(),b.begin(),b.end(),inserter(c,c.begin()));(交集)

    这表示有a从begin(迭代器)到end这段的集合和b的begin到end的这段的集合,将上述两者取并集or交集后塞到c的begin开始之后(inserter是什么?我也不知道就依葫芦画瓢用吧。。)。

    先放一开始写的代码,不知道上面那些玩意儿,思路比较狭窄,uva是RE了,uvalive和hdu上可以水过。

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<queue>
    #include<set>
    #include<map>
    #define dbg(x) cerr<<#x<<" = "<<x<<endl
    #define _dbg(x,y) cerr<<#x<<" = "<<x<<"   "<<#y<<" = "<<y<<endl
    using namespace std;
    typedef long long ll;
    template<typename T>inline char MIN(T&A,T B){return A>B?A=B,1:0;}
    template<typename T>inline char MAX(T&A,T B){return A<B?A=B,1:0;}
    template<typename T>inline T _min(T A,T B){return A<B?A:B;}
    template<typename T>inline T _max(T A,T B){return A>B?A:B;}
    template<typename T>inline T read(T&x){
        x=0;int f=0;char c;while(!isdigit(c=getchar()))if(c=='-')f=1;
        while(isdigit(c))x=x*10+(c&15),c=getchar();return f?x=-x:x;
    }
    const int N=2000+7;
    set<int> s[N];
    map<set<int>,int> mp;
    int T,m,tot,Top;
    char ch[14];
    struct thxORZ{
        int a[N],Top;
        inline void clear(){Top=0;}
        inline void push(){a[++Top]=1;}
        inline void copy(){++Top,a[Top]=a[Top-1];}
        inline void add(){
            --Top;if(s[a[Top]].find(a[Top+1])==s[a[Top]].end()){
                set<int> tmp=s[a[Top]];tmp.insert(a[Top+1]);
                map<set<int>,int>::iterator it=mp.find(tmp);
                if(it!=mp.end())a[Top]=it->second;
                else a[Top]=++tot,mp[tmp]=tot,s[tot]=tmp;
            }
        }
        inline void Union(){
            --Top;set<int> tmp=s[a[Top]];
            for(register set<int>::iterator it=s[a[Top+1]].begin();it!=s[a[Top+1]].end();++it)tmp.insert(*it);
            map<set<int>,int>::iterator it=mp.find(tmp);
            if(it!=mp.end())a[Top]=it->second;
            else a[Top]=++tot,mp[tmp]=tot,s[tot]=tmp;
        }
        inline void intersect(){
            --Top;set<int> tmp;tmp.clear();
            for(register set<int>::iterator it=s[a[Top]].begin();it!=s[a[Top]].end();++it)
                if(s[a[Top+1]].find(*it)!=s[a[Top+1]].end())tmp.insert(*it);
            map<set<int>,int>::iterator it=mp.find(tmp);
            if(it!=mp.end())a[Top]=it->second;
            else a[Top]=++tot,mp[tmp]=tot,s[tot]=tmp;
        }
        inline int print(){printf("%d
    ",s[a[Top]].size());}
    }thx;
    
    int main(){//freopen("test.in","r",stdin);freopen("test.out","w",stdout);
        read(T);while(T--){
            mp.clear();for(register int i=2;i<=tot;++i)s[i].clear();
            mp[s[1]]=tot=1;thx.clear();
            read(m);while(m--){
                scanf("%s",ch);
                switch(ch[0]){
                    case 'P':thx.push(),thx.print();break;
                    case 'D':thx.copy(),thx.print();break;
                    case 'A':thx.add(),thx.print();break;
                    case 'U':thx.Union(),thx.print();break;
                    case 'I':thx.intersect(),thx.print();break;
                }
            }
            puts("***");
        }
        return 0;
    }
    View Code

    下面这个是参考题解后improve过的,uva上就不会出错了,但是poj1000ms时限卡STL。。死活过不去,必须要写集合的hash使得log查找变成线性的。。我不会,算了算了逃了

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<algorithm>
    #include<queue>
    #include<vector>
    #include<map>
    #include<set>
    #define dbg(x) cerr<<#x<<" = "<<x<<endl
    #define _dbg(x,y) cerr<<#x<<" = "<<x<<"   "<<#y<<" = "<<y<<endl
    using namespace std;
    typedef long long ll;
    typedef set<int> thx;
    template<typename T>inline char MIN(T&A,T B){return A>B?A=B,1:0;}
    template<typename T>inline char MAX(T&A,T B){return A<B?A=B,1:0;}
    template<typename T>inline T _min(T A,T B){return A<B?A:B;}
    template<typename T>inline T _max(T A,T B){return A>B?A:B;}
    template<typename T>inline T read(T&x){
        x=0;int f=0;char c;while(!isdigit(c=getchar()))if(c=='-')f=1;
        while(isdigit(c))x=x*10+(c&15),c=getchar();return f?x=-x:x;
    }
    const int N=10000+7;
    vector<thx> s;
    map<thx,int> mp;
    int sta[N],t;
    int T,n;
    char opt[15];
    inline int get_ID(thx S){
        if(mp.find(S)!=mp.end())return mp[S];
        s.push_back(S);
        return mp[S]=s.size()-1;
    }
    inline void PUSH(){sta[++t]=0;}
    inline void DUP(){++t,sta[t]=sta[t-1];}
    inline void UNION(){
        thx tmp,s1=s[sta[t]],s2=s[sta[--t]];
        set_union(s1.begin(),s1.end(),s2.begin(),s2.end(),inserter(tmp,tmp.begin()));
        sta[t]=get_ID(tmp);
    }
    inline void INTERSECT(){
        thx tmp,s1=s[sta[t]],s2=s[sta[--t]];
        set_intersection(s1.begin(),s1.end(),s2.begin(),s2.end(),inserter(tmp,tmp.begin()));
        sta[t]=get_ID(tmp);
    }
    inline void ADD(){
        thx tmp=s[sta[--t]];
        tmp.insert(sta[t+1]);
        sta[t]=get_ID(tmp);
    }
    
    int main(){//freopen("test.in","r",stdin);freopen("test.out","w",stdout);
        thx orz;orz.clear();s.push_back(orz);mp[orz]=0;
        read(T);while(T--){
            t=0;
            read(n);while(n--){
                scanf("%s",opt);
                switch(opt[0]){
                    case 'P':PUSH();break;
                    case 'D':DUP();break;
                    case 'U':UNION();break;
                    case 'I':INTERSECT();break;
                    case 'A':ADD();break;
                }
                printf("%d
    ",s[sta[t]].size());
            }
            puts("***");
        }
        return 0;
    }
    View Code
  • 相关阅读:
    [LeetCode] 273. Integer to English Words 整数转为英文单词
    What happens when you type an URL in the browser and press enter?
    HTTP Status Code
    What's binary search?
    [Http] Difference between POST and GET?
    [LeetCode] 53. Maximum Subarray 最大子数组
    [LeetCode] 621. Task Scheduler 任务调度
    C# web项目添加*.ashx文件后报错处理
    Web项目和Windows应用程序的配置文件
    C#中web项目使用log4net日志
  • 原文地址:https://www.cnblogs.com/saigyouji-yuyuko/p/10888463.html
Copyright © 2011-2022 走看看