zoukankan      html  css  js  c++  java
  • 小和问题

    在一个数组中,每一个数左边比当前数小的数累加起来,叫做这个数组得小和.

    比如[1,3,4,2]1左边比1小的数没有,3左边比3小的数有1,4左边比4小的数有1,3,2左边比2小的数有1.那么这个数组的小和是

    1+1+3+1=6

     暴力方法是每次遍历的时候,都要再把前面的比较一下,这样时间复杂度是O(n^2)这样明显不行,仔细思考下过程,就是归并排序的过程之中,

    在你进行归并的时候,你需要左边比右边小的时候记录下来,进行累加,可以算出右边有多少个数比它大,代码如下:

    public static int getSmallSum(int[] a, int l, int r) {
            if (l >= r || a.length == 1)
                return 0;
            int mid = l + ((r - l) >> 1);
            //左边求小和加右边求小和加整体求整体小和
            return getSmallSum(a, l, mid) +
                    getSmallSum(a, mid + 1, r) +
                    process(a, l, mid, r);
        }
    
        private static int process(int[] a, int l, int mid, int r) {
            int[] aux = new int[r - l + 1];
            int lo = l;
            int hi = mid + 1;
            int index = 0;
            int sum = 0;
            while (lo <= mid && hi <= r) {
                if (a[lo] < a[hi]) {
                    //左边只有小才能算是小和,相等不算
                    sum = sum + (r - hi + 1) * a[lo];
                    aux[index++] = a[lo++];
                } else {
                    aux[index++] = a[hi++];
                }
            }
            while (lo <= mid) {
                aux[index++] = a[lo++];
            }
            while (hi <= r) {
                aux[index++] = a[hi++];
            }
            for (int aux1 : aux) {
                a[l++] = aux1;
            }
            return sum;
        }
  • 相关阅读:
    正则
    cookie、sesion
    POJ-1509
    HDU-3374
    ZOJ-3822
    HDU-5492
    在什么情况下Java比C++快?
    HDU-5451
    SPOJ-913
    莫比乌斯反演入门
  • 原文地址:https://www.cnblogs.com/junlancer/p/13079533.html
Copyright © 2011-2022 走看看