zoukankan      html  css  js  c++  java
  • [LintCode] Median(期望时间复杂度O(n)求中位数和第k大数)

     1 class Solution {
     2 public:
     3     /**
     4      * @param nums: A list of integers.
     5      * @return: An integer denotes the middle number of the array.
     6      */
     7     void swap(vector<int> &v, int i, int j)
     8     {
     9         int tmp = v[i];
    10         v[i] = v[j];
    11         v[j] = tmp;
    12     }
    13     int getMinK(vector<int> &v, int left, int right, int k)
    14     {
    15         if(left<right)
    16         {
    17             int i = left-1, j = left;
    18             for(; j<right;  ++j)
    19             {
    20                 if(v[j]<v[right])
    21                 {
    22                     ++i;
    23                     swap(v, i, j);
    24                 }
    25             }
    26             swap(v, i+1, right);
    27             if(k==i+1)  return v[i+1];
    28             else if(k<=i)   return getMinK(v, left, i, k);
    29             else return getMinK(v, i+2, right, k);
    30         }
    31         else    return v[left];
    32     }
    33     int median(vector<int> &v) {
    34         // write your code here
    35         return getMinK(v, 0, v.size()-1, (v.size()-1)/2);
    36     }
    37 };

    主要利用快排递归划分的思想,可以在期望复杂度为O(n)的条件下求第k大数。快排的期望复杂度为O(nlogn),因为快排会递归处理划分的两边,而求第k大数则只需要处理划分的一边,其期望复杂度将是O(n)。详细的证明见《算法导论》。

    我们可以这样粗略的思考:

    假设我们的数据足够的随机,每次划分都在数据序列的中间位置,那么第一次划分我们需要遍历约n个数,第二次需要遍历约n/2个数,...,这样递归下去,最后:n+n/2+n/(2^2)+n/(2^3)+...+n/(2^k)+... = (1+1/2+1/(2^2)+1/(2^3)+...+1/(2^k)+...)*n, 当k趋于无穷大的时候,上式的极限为2n。

  • 相关阅读:
    Vue2 组件注册
    Vue2 CSS 过渡
    Vue2 过滤器
    Vue2 路由
    网页一次滚动一屏幕效果
    JavaScript作用域-声明提升(个人总结)
    JS函数作用域提升
    如何以计算机的方式去思考
    常用Git命令总结
    关于RBAC(Role-Base Access Control)的理解(转)
  • 原文地址:https://www.cnblogs.com/pczhou/p/4684199.html
Copyright © 2011-2022 走看看