当需要在无需列表中寻找第k小的元素时,一个显然的方法是将所有数据进行排序,然后检索k个元素。这种方法的运行时间为O(n log(n))。

无序列表调用分区函数将自身分解成两个子表,其长度为i和n-i。第一个列表中的第一个i元素(不一定排序),当i与k进行比较时需在第一或第二个子列表中搜索元素。

使用findMinK(ArrayList<Integer>array, int k, int i, int r)实现,同时使用下面testframe代码测试。在函数中可增加全局变量cmpcnt,在列表中利用分区函数交换元素时计数。

对findMinK函数的实现,利用了快排的思想:

先从n个元素中找一个任意分界点,设为m,假设m在列表中的位置是i

先从n个元素中随便寻找一个数m作为分界点,m在列表中的位置为i

当 i = k时,m就是我们要寻找的第k小的数;

当 i > k时,我们就从1~i-1中查找;

当 i < k时,就从i+1~n中查找。

下面是代码实现:

package disorder_List;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Random; public class TestDisorder {
static public int cmpcnt = 0; public static void main(String[] args) {
testFramework(); } public static int partion(ArrayList<Integer> A,int low,int high){
int pivotkey=A.get(low); while(low<high){
while(low<high&&A.get(high)>=pivotkey)
high--;
A.set(low, A.get(high));
cmpcnt++;
while(low<high&& A.get(low)<pivotkey)
low++;
A.set(high, A.get(low));
cmpcnt++;
}
cmpcnt++;
A.set(low, pivotkey);
return low;
} public static int findMinK(ArrayList<Integer> array, int k, int l, int r) {
// Implement here
if(l<=r){
int pivotloc=partion(array, l, r);
if(pivotloc==k-1){
return array.get(pivotloc);
}
else if(pivotloc<(k-1)){
return findMinK(array, k,pivotloc+1,r);
}
else{
return findMinK(array, k,l,pivotloc-1);
}
}else
{
return -1;
} } public static int findMinK(ArrayList<Integer> array, int k){
Collections.sort(array);
return array.get(k-1);
} private static void testFramework() {
ArrayList<Integer> a = new ArrayList<Integer>();
for (int j=2;j<8;j++){
a.clear(); for (int i=0;i<(int)Math.pow(10, j);i++){
a.add(i);
}
System.out.println("nn"+a.size()+" Elementsnn");
double slow=0;
double fast=0; for (int i = 0; i < 2; i++) {
cmpcnt = 0;
Collections.shuffle(a); int k = (int)(Math.random()*(Math.pow(10, j)-1))+1; System.out.println("test run number: " + i + " find: " + k); long start = System.currentTimeMillis();
int resulta = findMinK(a, k, 0, a.size()-1);
long end = System.currentTimeMillis();
long smarttime=(end-start);
fast = fast + smarttime;
System.out.println("SMART ALGO t --- time in ms: " + smarttime + " comparisons: "
+ cmpcnt);
start = System.currentTimeMillis();
int resultb=findMinK(a, k);
end = System.currentTimeMillis();
long slowtime = (end-start);
System.out.println("WITH SORTING t --- time in ms: " + slowtime); slow = slow + slowtime;
}
System.out.println("sorting (="+slow+"ms) is " +slow/fast + " times slower than smart algo (="+fast+"ms)");
}
}
}

以下是部分输出结果:

sorting (=3.0ms) is 3.0 times slower than smart algo (=1.0ms)

sorting (=24.0ms) is 12.0 times slower than smart algo (=2.0ms)

sorting (=41.0ms) is 8.2 times slower than smart algo (=5.0ms)

sorting (=401.0ms) is 4.773809523809524 times slower than smart algo (=84.0ms)

....

可明显看出该方法的优势。

查询无序列表中第K小元素的更多相关文章

  1. ch1_5_2求无序序列中第k小的元素

    import java.util.Arrays; import java.util.PriorityQueue; public class ch1_5_2求无序序列中第k小的元素 { public s ...

  2. 有序矩阵中第k小元素

    有序矩阵中第k小元素 题目: 给定一个 n x n 矩阵,其中每行和每列元素均按升序排序,找到矩阵中第 k 小的元素. 请注意,它是排序后的第 k 小元素,而不是第 k 个不同的元素. 看到有序就会想 ...

  3. dfs 二叉树中序遍历迭代解法——求解BST中第k小元素

    BST中第K小的元素 中文English 给一棵二叉搜索树,写一个 KthSmallest 函数来找到其中第 K 小的元素. Example 样例 1: 输入:{1,#,2},2 输出:2 解释: 1 ...

  4. 找出数组[1...n]中第k小元素

    //问题描述: 试编写一个算法,使之能够在数组L[1...n]中找出第k小的元素(即从小到大排序后处于第k个位置的元素) #include <stdio.h> // 结合快排思想,查找第5 ...

  5. 快速排序-无序数组K小元素

    13:07:382020-03-10 11:16:13 问题描述: 找到一个无序数组中第K小的数 样例 1: 输入: [3, 4, 1, 2, 5], k = 3 输出: 3 样例 2: 输入: [1 ...

  6. 【Leetcode 堆、快速选择、Top-K问题 BFPRT】有序矩阵中第K小的元素(378)

    题目 给定一个 n x n 矩阵,其中每行和每列元素均按升序排序,找到矩阵中第k小的元素. 请注意,它是排序后的第k小元素,而不是第k个元素. 示例: matrix = [ [ 1, 5, 9], [ ...

  7. [LeetCode] Kth Smallest Element in a Sorted Matrix 有序矩阵中第K小的元素

    Given a n x n matrix where each of the rows and columns are sorted in ascending order, find the kth ...

  8. [Swift]LeetCode378. 有序矩阵中第K小的元素 | Kth Smallest Element in a Sorted Matrix

    Given a n x n matrix where each of the rows and columns are sorted in ascending order, find the kth ...

  9. Leetcode 378.有序矩阵中第k小的元素

    有序矩阵中第k小的元素 给定一个 n x n 矩阵,其中每行和每列元素均按升序排序,找到矩阵中第k小的元素.请注意,它是排序后的第k小元素,而不是第k个元素. 示例: matrix = [ [ 1, ...

随机推荐

  1. Oracle EBS-SQL (OM-3):销售连接停靠站时冲减库存出错处理.sql

    DELETE FROM INV.MTL_RESERVATIONS MRWHERE EXISTS (SELECT 1 FROM WSH.WSH_DELIVERY_ASSIGNMENTS WDA      ...

  2. 关于URL编码的问题

    在进行WEB开发时,字符集编码常常困扰着我们.我们需要区分两种情况,一是URL编码,二是HTTP Body编码.这两种编码所处理的机制不同. URL编码和解码 客户端负责对URL编码,服务端负责解码. ...

  3. sae python安装第三方模块

    sae python安装第三方模块 经过这一个星期的折腾,发现编程真心不是看出来的,真心是跟着书上的代码敲出来的.sae的服务做得很好,不过有时候会崩就是了.当sae上没有自己所需要的第三方模块时,可 ...

  4. java对象转json应clone,避免生成json串有问题

    今天因为一个java对象转json,搞了我一下午,在些记录一下: 是这样:我在strtuts2的action中调用services返回 Row: 26, 中国银行海鹰, 29, 东楼, 36, 1F ...

  5. Hive 4、Hive 的安装配置(远端MyMql模式)

    1.remote一体 这种存储方式需要在远端服务器运行一个mysql服务器,并且需要在Hive服务器启动meta服务.这里用mysql的测试服务器,ip位192.168.1.214,新建hive_re ...

  6. Android 菜单(OptionMenu)大全 建立你自己的菜单

    转自:http://www.cnblogs.com/salam/archive/2011/04/04/2005329.html 菜单是用户界面中最常见的元素之一,使用非常频繁,在Android中,菜单 ...

  7. jQuery 网格布局插件

    如今,大多数网站设计要靠网格系统和布局,这能够提供给设计人员一个方便的途径来组织网页上的内容.网格的设计最常见于报纸和杂志的版面,由文字和图像构成的列组成. 这篇文章给大家分享精心挑选的15款最佳的 ...

  8. JavaScript中模块“写法”

    在JavaScript模块到底是什么 event = function() { // do more return { bind: function() {}, unbind: function() ...

  9. plaidctf2015 ebp

    很容易看出是格式化字符串漏洞.这里的格式化字符串漏洞不像传统的那样,格式化字符串是放在bss段中,并没放在栈上,因此利用起来有些困难. 不过,我们可以利用ebp,可以修改函数的ebp,从而能控制函数的 ...

  10. Unicode解码、URL编码/解码

    + (NSString *) stringByReplaceUnicode:(NSString *)string { NSMutableString *convertedString = [strin ...