码迷,mamicode.com
首页 > 其他好文 > 详细

Templet

时间:2017-11-16 23:56:09      阅读:145      评论:0      收藏:0      [点我收藏+]

标签:算法   loop   prim   中国剩余定理   else   mod   long   use   UI   

KMP

void getnext(){

    int q, k;

    next1[0] = 0;

    for(q = 1, k = 0; q < m; q++){

        while(k > 0 && sh[q] != sh[k])

            k = next1[k-1];

        if(sh[q] == sh[k])

            k++;

        next1[q] = k;

    }

}

int kmp(){

    int i, q;

    int ans = 0;

    for(i = 0, q = 0; i < n; i++){

        while(q > 0 && sh[q] != ch[i])

            q = next1[q-1];

        if(sh[q] == ch[i])

            q++;

        if(q == m)

            ans++;

    }

    return ans;

}

字典树

typedef struct Trie{

       Trie *next[MAX];

       int v;

}Trie;

Trie *root;

void createTrie(char *str){

       int len = strlen(str);

       Trie *p = root, *q;

       for(int i = 0; i < len; i++){

              int id = str[i] - ‘0‘;

              if(p->next[id] == NULL){

                     q =(Trie *)malloc(sizeof(Trie));

                     q->v = 1;

                     for(int j = 0; j < MAX; j++){

                            q->next[j] = NULL;

                     }

                     p->next[id] = q;

                     p = p->next[id];

              }

              else{

                     p->next[id]->v++;

                     p = p->next[id];

              }

       }

       p->v = -1;

}

int findTrie(char *str){

       int len = strlen(str);

       Trie *p = root;

       for(int i = 0; i < len; i++){

              int id = str[i] -‘0‘;

              p = p->next[id];

              if(p == NULL)

                     return 0;

              if(p->v == -1)

                     return -1;

       }

       return -1;

}

void delete_(Trie *g){

       if(g==NULL)

              return;

       for(int i = 0; i < MAX; i++){

              if(g->next[i] != NULL)

                     delete_(g->next[i]);

       }

       free(g);

       return;

}

AC自动机

struct node{

       node *next[26];

       node *fail;

       int sum;

}*root, *q[10000000]

void createTrie(char *str){

       node *p = root, *q;

       int len = strlen(str);

       for(int i = 0; i < len; i++){

              int id = str[i] - ‘a‘;

              if(p->next[id] == NULL){

                     q = (struct node *)malloc(sizeof(struct node));

                     for(int j = 0; j < 26; j++)

                            q->next[j] = 0;

                     q->sum = 0;

                     q->fail = 0;

                     p->next[id] = q;

              }

              p = p->next[id];

       }

       p->sum++;

}

void build_fail_pointer(){

       head = 0,tail = 1;

       q[head] = root;

       node *p, *temp;

       while(head<tail){

              temp = q[head++];

              for(int i = 0; i < 26; i++){

                     if(temp->next[i]){

                            if(temp == root)

                                   temp->next[i]->fail = root;

                            else{

                                   p = temp->fail;

                                   while(p){

                                          if(p->next[i]){

                                                 temp->next[i]->fail = p->next[i];

                                                 break;

                                          }

                                          p = p->fail;

                                   }

                                   if(p == NULL)

                                          temp->next[i]->fail = root;

                            }

                            q[tail++] = temp->next[i];

                     }

              }

       }

}

void ac_automation(char *str){

       node *p = root;

       int len = strlen(str);

       for(int i = 0; i < len; i++){

              int id = str[i] - ‘a‘;

              while(!p->next[id] && p != root)

                     p = p->fail;

              p = p->next[id];

              if(!p)

                     p = root;

              node *temp = p;

              while(temp != root){

                     if(temp->sum >= 0){

                            cnt += temp->sum;

                            temp->sum = -1;

                     }

                     else break;

                     temp = temp->fail;

              }

       }

}

主席树

void Build(int& o, int l, int r){

    o = ++ tot;

    sum[o] = 0;

    if(l == r) return;

    int m = (l + r) >> 1;

    Build(ls[o], l, m);

    Build(rs[o], m + 1, r);

}

void update(int& o, int l, int r, int last, int p){

    o = + +tot;

    ls[o] = ls[last];

    rs[o] = rs[last];

    sum[o] = sum[last] + 1;

    if(l == r) return;

    int m = (l + r) >> 1;

    if(p <= m)  update(ls[o], l, m, ls[last], p);

    else update(rs[o], m + 1, r, rs[last], p);

}

int query(int ss, int tt, int l, int r, int k){

    if(l == r) return l;

    int m = (l + r) >> 1;

    int cnt = sum[ls[tt]] - sum[ls[ss]];

    if(k <= cnt) return query(ls[ss], ls[tt], l, m, k);

    else return query(rs[ss], rs[tt], m + 1, r, k - cnt);

}

int main(){

    scanf("%d", &T);

    while(T--){

        scanf("%d%d", &n, &q);

        for(int i = 1; i <= n; i ++) scanf("%d", a + i), b[i] = a[i];

        sort(b + 1, b + n + 1);

        sz = unique(b + 1, b + n + 1) - (b + 1);

        tot = 0;

        Build(rt[0],1, sz);

        //for(int i = 0; i <= 4 * n; i ++)

//printf("%d,rt =  %d,ls =  %d, rs = %d, sum = %d\n", i, rt[i], ls[i], rs[i], sum[i]);

        for(int i = 1; i <= n; i ++)

            a[i] = lower_bound(b + 1, b + sz + 1, a[i]) - b;

        for(int i = 1; i <= n; i ++)

            update(rt[i], 1, sz, rt[i - 1], a[i]);

        //for(int i = 0; i <= 5 * n; i++)

        //printf("%d,rt =  %d, ls = %d, rs = %d, sum = %d\n", i, rt[i], ls[i], rs[i], sum[i]);

        while(q --)work();

    }

    return 0;

}

SA

int A[MAX_N];

int rev[MAX_N*2], sa[MAX_N *2];

int n,k;

int rank1[MAX_N], tmp[MAX_N];

bool compare_sa(int i, int j){

    if(rank1[i] != rank1[j])

        return rank1[i] < rank1[j];

    int ri = i + k <= n ? rank1[i+k] : -1;

    int rj = j + k <= n ? rank1[j+k] : -1;

    return ri < rj;

}

void construct_sa(int sh[],int n,int *sa){

    for(int i = 0; i <= n; i++){

        sa[i] = i;

        rank1[i] = i < n ? sh[i] : -1;

    }

    for(k = 1; k <= n; k *= 2){

        sort(sa, sa + n + 1, compare_sa);

        tmp[sa[0]] = 0;

        for( int i = 1; i <= n; i++){

            tmp[sa[i]] = tmp[sa[i-1]] + (compare_sa(sa[i-1], sa[i])? 1 : 0);

        }

        for(int i = 0; i <= n; i++){

            rank1[i] = tmp[i];

        }

    }

}

void solve(){

    reverse_copy(A, A+n, rev);

    construct_sa(rev, n, sa);

    int p1;

    for(int i = 0; i < n; i++){

        p1 = n - sa[i];

        if(p1 >= 1 && n - p1 >=2)

            break;

    }

    int m = n-p1;

    reverse_copy(A+p1, A+n, rev);

    reverse_copy(A+p1, A+n, rev+m);

    construct_sa(rev, m*2, sa);

    int p2;

    for(int i = 0; i <= 2*n; i++){

        p2 = p1 + m -sa[i];

        if(p2 - p1 >= 1 && n - p2 >= 1)

            break;

    }

    reverse(A, A+p1);

    reverse(A+p1, A+p2);

    reverse(A+p2, A+n);

    for(int i = 0; i < n; i++)

        printf("%d\n", A[i]);

}

SA—LCP

void construct_lcp(string S, int *sa, int *lcp){

    for(int i = 0; i <= n; i++)

        rank1[sa[i]] = i;

    int h = 0;

    lcp[0] = 0;

    for(int i = 0; i < n; i++){

        int j = sa[rank1[i] - 1];

        if(h > 0) h--;

        for(; j + h < n && i + h < n; h++)

            if(S[j+h] != S[i+h])

                break;

        lcp[rank1[i]-1] = h;

    }

}

中国剩余定理

ll China(ll *m,ll *a)

{

    ll M=1,d,y,x=0;

for(int i=0;i<n;i++)

M*=m[i];

    for(int i=0;i<n;i++){

        ll w=M/m[i];

        gcd(m[i],w,d,d,y);

        x=(x+y*w*a[i])%M;

    }

    return (x+M)%M;

}

 

扩展欧几里得算法

void ex_gcd(ll a,ll b,ll &d,ll &x,ll &y)

{

    if(b==0){

        d=a;

        x=1,y=0;

    }

    else{

        gcd(b,a%b,d,y,x);

        y-=(a/b)*x;

    }

}

 

最短路

struct edge{int from, to, cost};

void shortpath(int s){

    for(int i = 0; i < V; i++) d[i] = INF;

    d[s] = 0;

    while(1){

        bool update = false;

        for(int i = 0; i < E; i++){

            edge e = es[i];

            if(d[e.from] != INF && d[e.to] > d[e.from] + e.cost){

                d[e.to] = d[e.from] + e.cost;

                update = true;

            }

        }

        if(!update) break;

    }

}

 

bool find_negative_loop(){

    memset(d,0,sizeof(d));

    for(int i = 0; i < n; i++)

    {

        for(int j = 0; j < m+w+m; j++)

        {

            edge e = ed[j];

            if(d[e.to] > d[e.from] + e.cost)

            {

                d[e.to] = d[e.from] + e.cost;

 

                if(i == n-1)

                    return true;

            }

        }

    }

    return false;

}

 

void floyd(int m){//}O(m^3)

    for(int i = 0; i < m; i++)

        for(int k = 0; k < m; k++)

            for(int j = 0; j < m; j++)

                d[k][j] = min(d[k][j], d[k][i] + d[i][j]);

}

 

struct edge{

    int to,cost;

    edge(){}

    edge(int to, int cost) : to(to), cost(cost){}

};

vector<edge> g[Max];

typedef pair<int, int> P;

void dijkstra(int s){

    priority_queue<P, vector<P>, greater<P> > que;

    memset(d[s], 0x3f3f, Max * sizeof(int));

    d[s][s] = 0;

    que.push(P(0, s));

    while(que.size())

    {

        P p = que.top(); que.pop();

        int v = p.second;

        if(d[s][v] < p.first) continue;

        for(int i = 0; i < g[v].size(); i++)

        {

            edge e = g[v][i];

            if(d[s][e.to] > d[s][v] + e.cost)

            {

                d[s][e.to] = d[s][v] + e.cost;

                que.push(P(d[s][e.to], e.to));

            }

        }

    }

    return ;

}

生成树

struct edge{

    int x, y, d;

    const bool operator < (const edge& o) const { return d < o.d; }

}zhen[500002];

 

void initialize(){

    for(int i = 1; i < N; i++) par[i] = i, _rank[i] = 0;

}

int find(int x){

    if(x == par[x]) return x;

    return par[x] = find(par[x]);

}

void unit(int x, int y){

    int xx = find(x), yy = find(y);

    if(xx == yy) return;

    if(_rank[xx] < _rank[yy]) par[xx] = yy;

    else

        par[yy] = xx;

    if(_rank[xx] == _rank[yy]) _rank[x]++;

}

bool is_thesame(int x, int y){ return find(x) == find(y); }

 

void kruskal(){

    sort(ch, ch + E, cmp);

    for(int i = 0; i < E; i++)

    if(isthesame(ch[i].x, n + ch[i].y)) 

        ans += ch[i].cost;

}

 

Int d[maxn][maxn], mincost[maxn];

bool used[maxn];

int prim(){

    for(int i = 0; i < 102; i++)

    {

        mincost[i] = INF;

        used[i] = false;

    }

    mincost[0] = 0;

    int ans = 0;

    while(true)

    {

        int flag = -1;

        for(int i = 0; i < n; i++)

            if(!used[i] && (flag == -1 || mincost[i]< mincost[flag]))

                flag = i;

        if(flag == -1)

            break;

        used[flag] = true;

        ans += mincost[flag];

        for(int i = 0; i < n; i++)

            mincost[i] = min(mincost[i], d[flag][i]);

    }

    return ans;

}

快速幂

ll mod_pow(ll x, ll n, ll mod){

       ll res = 1;

       while(n>0){

              if(n&1) res = res * x % mod;

              x = x * x % mod;

              n >>= 1;

}

return res;

}

尺取

int res = n+1;

int s = 0, t = 0, sum = 0;

while(1){

    while(t<n && sum < S){//长度最短为S

        sum+=a[t++];

    }

    if(sum < S) break;

    res = min(res, t-s);

    sum -= a[s++];

}

if(res > n)

res = 0;

线段树

long long ch[100010];

long long sum;

long long Stree[100010<<2],lazy[100010<<2];

 

void build(int root, int l, int r){

    lazy[root] = 0;

    if(l == r)

        Stree[root] = ch[l];

    else{

        int mid = (l+r)/2;

        build(root*2, l, mid);

        build(root*2+1, mid + 1, r);

        Stree[root] = Stree[root*2] + Stree[root*2+1];

    }

}

void pushdown(int root,int num){

    if(lazy[root]){

        Stree[root*2] += 1LL*(num-(num>>1))*lazy[root];

        Stree[root*2+1] += 1LL*(num>>1)*lazy[root];

        lazy[root*2] += lazy[root];

        lazy[root*2+1] += lazy[root];

        lazy[root] = 0;

    }

}

void add(int root, int L, int R, int l, int r, long long ad){

    if(L>r || R < l) return;

    if(R<=r && L>=l){

        Stree[root] += 1LL*(R-L+1)*ad;

        lazy[root] += ad;

        return ;

    }

    pushdown(root,R-L+1);

    int mid = (L+R) >> 1;

    add(root*2, L, mid, l, r, ad);

    add(root*2+1, mid+1, R, l, r, ad);

    Stree[root] = Stree[root*2] + Stree[root*2+1];

}

void query(int root, int L, int R, int l, int r){

    if(L>r || R < l) return;

    if(l <= L && R <= r){

        sum += Stree[root];

        return ;

    }

    pushdown(root,R-L+1);

    int mid = (L+R) >> 1;

    query(root*2, L, mid, l, r);

    query(root*2+1, mid+1, R, l, r);

}

BIT_Tree

int lowbit(int i) 

return i&(-i); 

void update(int i, int val)

    while(i <= n)  

    { 

        a[i] += val; 

        i += lowbit(i); 

    } 

int sum(int i) 

    int sum = 0; 

    while(i > 0) 

    { 

        sum += a[i]; 

        i -= lowbit(i); 

    } 

    return sum; 

 

 

 

Templet

标签:算法   loop   prim   中国剩余定理   else   mod   long   use   UI   

原文地址:http://www.cnblogs.com/tony-/p/7846722.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!