zoukankan      html  css  js  c++  java
  • 一些神奇的(优化)板子——来自Loi_black的博客

    deque<int>q;
    void spfa(int s)
    {
        for(int i=1;i<=n;i++)
            d[i]=1e9;
        d[s]=0;
        q.push_back(s);
        used[s]=1;
        while(!q.empty())
        {
            int x=q.front();
            q.pop_front();
            used[x]=0;
            for(int i=first[x];i;i=next[i])
            {
                int u=hh[i].t;
                if(d[u]>d[x]+hh[i].c)
                {
                    d[u]=d[x]+hh[i].c;
                    if(!used[u])
                    {
                        used[u]=1;
                        if(!q.empty())
                        {
                            if(d[u]<d[q.front()])
                                q.push_front(u);
                            else
                                q.push_back(u);
                        }
                        else
                            q.push_back(u);
                    }
                }
            }
        }
    }   
    //spfa+(slf优化)
    int tim[maxn];
    bool spfa(int s)
    {
        d[s]=0;
        q.push(s);
        used[s]=1;
        while(!q.empty())
        {
            int x=q.front();
            q.pop();
            used[x]=0;
            for(int i=first[x];i;i=next[i])
            {
                int u=hh[i].t;
                if(d[u]>d[x]+hh[i].c)
                {
                    d[u]=d[x]+hh[i].c;
                    if(!used[u])
                    {
                        if(++tim[u]>n)
                            return false;
                        q.push(u);
                        used[u]=1;
                    }
                }
            }
        }
        return true;
    }
    
    //spfa判负环
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    #include<queue>
    using namespace std;
    const int maxn=200005;
    struct dqs
    {
        int f,t,c;
    }hh[maxn];
    struct dqm
    {
        int num,dis;
    };
    bool operator <(dqm a,dqm b)
    {
        return a.dis>b.dis;
    }
    int tot=0,first[maxn],next[maxn],d[maxn];
    bool used[maxn];
    void build(int f,int t,int c)
    {
        hh[++tot]=(dqs){f,t,c};
        next[tot]=first[f];
        first[f]=tot;
    }
    priority_queue<dqm>q;
    void dij(int s)
    {
        d[s]=0;
        q.push({s,d[s]});
        while(!q.empty())
        {
            int head = q.top().num;
            q.pop();
            used[head]=1;
            for(int i=first[head];i;i=next[i])
            {
                int u=hh[i].t;
                if(d[u]>d[head]+hh[i].c)
                {
                    d[u]=d[head]+hh[i].c;
                    if(!used[u])
                        q.push((dqm){u,d[u]});
                }
            }
        }
    }
    int main()
    {
        int n,m,s,e;
        scanf("%d%d%d%d",&n,&m,&s,&e);
        ......
    }
    //dijkstra+ 堆
    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cstring>
    using namespace std;
    const int maxn=250010;
    struct dqs
    {
        int f,t,c;
    }hh[maxn<<1];
    int tot=0,fa[maxn][31],next[maxn],first[maxn],f[maxn],d[maxn];
    void build(int ff,int tt,int cc)
    {
        hh[++tot]=(dqs){ff,tt,cc};
        next[tot]=first[ff];
        first[ff]=tot;
    }
    int deep[maxn];
    void dfs(int x,int sd)
    {
        deep[x]=sd;
        int u;
        for(int i=first[x];i;i=next[i])
        {
            u=hh[i].t;
            if(!deep[u]&&u)
            {
                f[u]=x;
                d[u]=d[x]+hh[i].c;
                dfs(u,sd+1);
            }
        }
    }
    int lca(int x,int y)
    {
        if(deep[x]<deep[y])
        swap(x,y);
        int deepcha=deep[x]-deep[y];
        for(int i=0;i<=30;i++)
        {
            if(1<<i&deepcha)
            x=fa[x][i];
        }
        for(int i=30;i>=0;i--)
        {
            if(fa[x][i]!=fa[y][i])
            {
                x=fa[x][i];
                y=fa[y][i];
            }
        }
        if(x!=y)
            return f[x];
        return x;
    }
    int main()
    {
        int n;
        scanf("%d",&n);
        int u,v,c;
        for(int i=1;i<n;i++)
        {
            scanf("%d%d%d",&u,&v,&c);
            build(u,v,c);
            build(v,u,c);
        }
        dfs(0,0);
        for(int i=0;i<n;i++)
            fa[i][0]=f[i];
        for(int j=1;j<=20;j++)
        for(int i=1;i<=n;i++)
            fa[i][j]=fa[fa[i][j-1]][j-1];
        int m;
        scanf("%d",&m);
        for(int i=1;i<=m;i++)
        {
            scanf("%d%d",&u,&v);
            int xx=lca(u,v);
            printf("%d
    ",d[u]+d[v]-2*d[xx]);
        }
        return 0;
    }
    
    //倍增lca
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    #include<queue>
    using namespace std;
    const int maxn=200005;
    struct dqs
    {
        int f,t,c;
    }hh[maxn];
    int tot=0,first[maxn],next[maxn],du[maxn];
    void build(int f,int t)
    {
        hh[++tot]=(dqs){f,t};
        next[tot]=first[f];
        first[f]=tot;
    }
    queue<int>q;
    void tp()
    {
        while(!q.empty())
        {
            int x=q.front();
            q.pop();
            printf("%d ",x);
            for(int i=first[x];i;i=next[i])
            {
                int u=hh[i].t;
                du[u]--;
                if(!du[u])
                q.push(u);
            }
        }
    }
    int main()
    {
        int n;
        scanf("%d",&n);
        for(int i=1;i<=n;i++)
        {
            int x;
            while(true)
            {
                scanf("%d",&x);
                if(x==0)
                break;
                build(i,x);
                du[x]++;
            }
        }
        for(int i=1;i<=n;i++)
            if(!du[i])
                q.push(i);
        tp();
        return 0;
    }
    //拓扑排序
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    using namespace std;
    const int maxn=10005;
    struct dqs
    {
        int f,t;
    }hh[maxn];
    int tot=0;
    int first[maxn],next[maxn];
    void build(int f,int t)
    {
        hh[++tot]=(dqs){f,t};
        next[tot]=first[f];
        first[f]=tot;
    }
    int dfn[maxn],low[maxn],stack[maxn],size[maxn],du[maxn],jlqlt[maxn];
    bool in_stack[maxn];
    int tot1=0,cnt=0,snum=0;
    void group(int x)
    {
        dfn[x]=low[x]=++tot1;
        stack[++snum]=x;
        in_stack[x]=1;
        for(int i=first[x];i;i=next[i])
        {
            int u=hh[i].t;
            if(!dfn[u])
            {
                group(u);
                low[x]=min(low[x],low[u]);
            }
            else if(in_stack[u])
                low[x]=min(low[x],dfn[u]);
        }
        if(dfn[x]==low[x])
        {
            cnt++;
            while(true)
            {
                jlqlt[stack[snum]]=cnt;
                in_stack[stack[snum]]=0;
                size[cnt]++;
                snum--;
                if(stack[snum+1]==x)
                    break;
            }
        }
    }
    int main()
    {
        int n,m;
        scanf("%d%d",&n,&m);
        for(int i=1;i<=m;i++)
        {
            int a,b;
            scanf("%d%d",&a,&b);
            build(a,b);
        }
        for(int i=1;i<=n;i++)
            if(!dfn[i])
                group(i);
        for(int i=1;i<=n;i++)
            for(int j=first[i];j;j=next[j])
            {
                int u=hh[j].t;
                if(jlqlt[i]!=jlqlt[u])
                    du[jlqlt[i]]++;
            }
        int sum1=0,sum2=0,x;
        for(int i=1;i<=cnt;i++)
        {
            if(size[i]>1)
                sum1++;
            if(!du[i])
            {
                sum2++;
                x=i;        
            }
        }
        printf("%d
    ",sum1);
        if(sum2==1&&size[x]!=1)
        {
            for(int i=1;i<=n;i++)
            {
                if(jlqlt[i]==x)
                printf("%d ",i);
            }
        }
        else
        printf("-1
    ");
        return 0;
    } 
    
    //trajan
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    using namespace std;
    const int maxn=200005; 
    long long tmp[maxn],a[maxn];
    long long ans=0;
    void merge(int l,int mid,int r)
    {
        int i=l,j=mid+1,k=l;
        while(i<=mid&&j<=r)
        {
            if(a[i]>a[j])
            {
                tmp[k++]=a[j++];
                ans+=mid+1-i;
            }
            else
                tmp[k++]=a[i++]; 
        }
        while(i<=mid)
            tmp[k++]=a[i++];
        while(j<=r)
            tmp[k++]=a[j++];
        for(int i=l;i<=r;i++)
            a[i]=tmp[i];
    }
    void merge_sort(int l,int r)
    {
        if(l<r)
        {
            int mid=(l+r)>>1;
            merge_sort(l,mid);
            merge_sort(mid+1,r);
            merge(l,mid,r);
        } 
    }
    int main()
    {
        int n;
        scanf("%d",&n);
        for(int i=1;i<=n;i++)
            scanf("%lld",&a[i]);
        merge_sort(1,n);
        for(int i=1;i<=n;i++)
            cout<<a[i]<<" ";
        cout<<endl;
        printf("%lld",ans);
    }
    
    //归并排序
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    using namespace std;
    const int maxn=200005;
    int heap[maxn],cnt=0;
    void push(int x)
    {
        cnt++;
        int now=cnt;
        heap[now]=x;
        while(now>1)
        {
            if(heap[now]<heap[now/2])
            {
                swap(heap[now],heap[now/2]);
                now/=2;
            }
            else break;
        }
    }
    void pop()
    {
        heap[1]=heap[cnt];
        int now=1;
        while(now*2+1<=cnt)
        {
            int l=now*2,r=now*2+1;
            if(heap[l]<heap[now])
            {
                if(heap[r]<heap[l])
                    swap(l,r);
                swap(heap[l],heap[now]);
                now=l;
            }
            else if(heap[r]<heap[now])
            {
                swap(heap[r],heap[now]);
                now=r;
            }
            else break;
        }
        cnt--;
    }
    int main()
    {
        int n;
        scanf("%d",&n);
        for(int i=1;i<=n;i++)
        {
            int x;
            scanf("%d",&x);
            push(x);
        }
        for(int i=1;i<=n;i++)
        {
            printf("%d ",heap[1]);
            pop();
        }
    }
    
    //手打最小堆(最大堆同理)
  • 相关阅读:
    高等代数中的名词解析No1
    概率论中的名词解释(个人理解,非官方) No1
    概率论中的公式解释(个人理解,非官方) No1
    CentOS7 网络设置
    神经网络与人工智能No0导言(笔记版)
    centos7 防火墙设置
    神经网络与人工智能No1Rosenblatt感知器(笔记版)
    输入法打不出来的数学符号大全
    php对xml文件的解析
    PHPExcel生成Excel模版
  • 原文地址:https://www.cnblogs.com/ZDHYXZ/p/7636640.html
Copyright © 2011-2022 走看看