zoukankan      html  css  js  c++  java
  • bzoj4567: [Scoi2016]背单词

    d1t1,比较良心。虽然感觉我写得比较鬼畜。

    容易看出一种贪心的思路,把串按后缀关系分组,不同组分开考虑,同组的放一块儿写,然后组的size小的靠前写是一个最优的方案。

    同组的也可以同样递归下去考虑。

    于是先建出字典树,然后把后缀关系的树建出来,在这颗树上贪心。

    注意需要在这颗后缀关系树上贪心(把儿子按size大小排序),不能直接在字典树上贪心(一个size大的的儿子不一定是同一组后缀关系)。

    //Achen
    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<cstdlib>
    #include<vector>
    #include<cstdio>
    #include<queue>
    #include<cmath>
    const int N=1010007;
    typedef long long LL;
    using namespace std;
    int n;
    char s[N];
    LL ans;
    
    template<typename T>void read(T &x)  {
        char ch=getchar(); x=0; T f=1;
        while(ch!='-'&&(ch<'0'||ch>'9')) ch=getchar();
        if(ch=='-') f=-1,ch=getchar();
        for(;ch>='0'&&ch<='9';ch=getchar()) x=x*10+ch-'0'; x*=f;
    }
    
    int ch[N][26],is[N],sz[N],rt,tot;
    void insert(int len) {
        int x=rt;
        for(int i=len-1;i>=0;i--) {
            int c=s[i]-'a';
            if(!ch[x][c]) ch[x][c]=++tot;
            x=ch[x][c];
        }
        is[x]=1;
    }
    
    bool cmp(const int &A,const int &B) {
        return sz[A]<sz[B]; 
    }
    
    vector<int>son[N];
    void add(int u,int v) { son[u].push_back(v); }
    
    int pos,p[N];
    void dfs1(int x,int fa) {
        if(is[x]) 
            add(fa,x);
        for(int i=0;i<26;i++) if(ch[x][i]) 
            dfs1(ch[x][i],is[x]?x:fa);
    }
    
    void dfs2(int x) {
        int up=son[x].size();
        sz[x]=1;
        for(int i=0;i<up;i++) {
            int y=son[x][i];
            dfs2(y); sz[x]+=sz[y];
        }
    }
    
    void dfs3(int x,int pr) {
        sort(son[x].begin(),son[x].end(),cmp);
        int up=son[x].size();
        if(x!=0) ++pos; 
        int tp=pos;
        ans+=tp-pr; 
        for(int i=0;i<up;i++) {
            int y=son[x][i];
            dfs3(y,tp);
        }
    }
    
    int main() {
        //freopen("1.in","r",stdin);
        read(n);
        for(int i=1;i<=n;i++) {
            scanf("%s",s);
            int len=strlen(s);
            insert(len);
        }
        dfs1(rt,0);
        dfs2(rt);
        dfs3(rt,0);
        printf("%lld
    ",ans);
        return 0;
    }
    View Code
  • 相关阅读:
    iOS中的HTTPS
    HTTPS抓包之Charles
    组件化开发的一些思考
    Xcode 调试技巧
    iOS崩溃日志分析
    iOS依赖库管理工具之Carthage
    13.类的关系总结
    12.组合(Composition)
    11.聚合(Aggregation)
    10.关联(Association)
  • 原文地址:https://www.cnblogs.com/Achenchen/p/8407071.html
Copyright © 2011-2022 走看看