zoukankan      html  css  js  c++  java
  • 牛客(35)数组中的逆序对

    //    题目描述
    //    在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。
    //    输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007}
    
    //    题目保证输入的数组中没有的相同的数字
    //
    //    数据范围:
    //
    //    对于%50的数据,size<=10^4
    //
    //    对于%75的数据,size<=10^5
    //
    //    对于%100的数据,size<=2*10^5
    
    //    public static int InversePairs(int[] array) {
    ////        超时
    //        int count = 0;
    //        for (int i=0; i<array.length;i++){
    //            for (int j=i+1;j<array.length;j++){
    //                if (array[i]>=array[j]){
    //                    count++;
    //                }
    //            }
    //        }
    //        return count%1000000007;
    //    }
    
        public static int InversePairs(int[] arr) {
            int[] temp = new int[arr.length];//在排序前,先建好一个长度等于原数组长度的临时数组,避免递归中频繁开辟空间
            return sort(arr, 0, arr.length - 1, temp);
        }
    
        private static int sort(int[] arr, int left, int right, int[] temp) {
            if (left >= right) {
                return 0;
            }
            int count = 0;
            int mid = (left + right) / 2;
            int leftCount = sort(arr, left, mid, temp);//左边归并排序,使得左子序列有序
            int rightCount = sort(arr, mid + 1, right, temp);//右边归并排序,使得右子序列有序
    
    
            int i= mid;
            int j=right;
            while (i>=left&&j>mid){
                if (arr[i]>arr[j]){
                    count += j-mid;
                    //不加判断通过50%
                    if(count>=1000000007)//数值过大求余
                    {
                        count%=1000000007;
                    }
                    i--;
                }else{
                    j--;
                }
            }
            merge(arr, left, mid, right, temp);//将两个有序子数组合并操作
            //75%通过
    //        return count + leftCount + rightCount;
            return (count + leftCount + rightCount)%1000000007;
        }
    
        private static void merge(int[] arr, int left, int mid, int right, int[] temp) {
            int i = left;//左序列指针
            int j = mid + 1;//右序列指针
            int t = 0;//临时数组指针
            while (i <= mid && j <= right) {
                if (arr[i] <= arr[j]) {
                    temp[t++] = arr[i++];
                } else {
                    temp[t++] = arr[j++];
                }
            }
            while (i <= mid) {//将左边剩余元素填充进temp中
                temp[t++] = arr[i++];
            }
            while (j <= right) {//将右序列剩余元素填充进temp中
                temp[t++] = arr[j++];
            }
            t = 0;
            //将temp中的元素全部拷贝到原数组中
            while (left <= right) {
                arr[left++] = temp[t++];
            }
        }
  • 相关阅读:
    Rainmeter 雨滴桌面 主题分享
    行人检測之HOG特征(Histograms of Oriented Gradients)
    const和readonly差别
    ADB命令解析
    Java实现 蓝桥杯VIP 算法训练 接水问题
    Java实现 蓝桥杯VIP 算法训练 星际交流
    Java实现 蓝桥杯VIP 算法训练 星际交流
    Java实现 蓝桥杯VIP 算法训练 星际交流
    Java实现 蓝桥杯VIP 算法训练 星际交流
    Java实现 蓝桥杯VIP 算法训练 星际交流
  • 原文地址:https://www.cnblogs.com/kaibing/p/9046474.html
Copyright © 2011-2022 走看看