zoukankan      html  css  js  c++  java
  • 逆序对

    输入一个序列求序列中的逆序对

    归并排序代码

    void merge_sort(int *a,int x,int y,int *T)
    {
    if(y-x<=1)return ;
    int m=x+(y-x)/2;
    int p=x,q=m,i=x;
    merge_sort(a,x,m,T);
    merge_sort(a,m,y,T);
    while(p<m||q<y)
    {
    if(q>=y||(p<m&&a[p]<=a[q]))
    T[i++]=a[p++];
    else
    T[i++]=a[q++];
    }
    for(int x;i<y;i++)a[i]=T[i];
    }
    //代码来自紫书

    分治方法,先分开,然后递归求解,最后合并问题。

    将序列分成差不多等长的两部分,统计i和j均在左边或者均在右边的逆序对数,再统计i在左边,j在右边的逆序对数。

    求i,j分别在两边的情况,可以通过上面的排序算法所用的技巧算,因为归并排序最后合并i在左j在右,并且两边有序所以每一次找到a[p]>a[q]就可以判定为是逆序,并且可以判定a[p]到a[m]中间的都大于a[q]。于是 可以直接cnt+=m-p。

    #include<iostream>
    using namespace std;
    int a[100];
    int t[100];
    int cnt=0;
    void merge_sort(int *a,int x,int y,int *T)
    {
        if(y-x>1)
        {
            int m=x+(y-x)/2;
            int p=x,q=m,i=x;
            merge_sort(a,x,m,T);
            merge_sort(a,m,y,T);
            while(p<m||q<y)
            {
                if(q>=y||(p<m&&a[p]<=a[q]))
                    T[i++]=a[p++];
                else
                    {T[i++]=a[q++];cnt+=m-p;}
            }
            for(i=x;i<y;i++)
                a[i]=T[i];
        }
    }
    int main()
    {
        int n;
        cin>>n;
        for(int i=0;i<n;i++)
            cin>>a[i];
        merge_sort(a,0,n,t);
        cout<<cnt<<endl;
    }
    //代码来自对紫书上修改
  • 相关阅读:
    Zabbix5 Frame 嵌套
    Zabbix5 对接 SAML 协议 SSO
    CentOS7 安装 Nexus
    CentOS7 安装 SonarQube
    GitLab 后台修改用户密码
    GitLab 查看版本号
    GitLab Admin Area 500 Error
    Linux 安装 PostgreSQL
    Liger ui grid 参数
    vue.js 是一个怪东西
  • 原文地址:https://www.cnblogs.com/ke-yi-/p/10175820.html
Copyright © 2011-2022 走看看