public static int kthLargestElement(int k, int[] nums) { //两个哨兵ij,temp为临时值,start和end记录具体查找段的开始和结束 int i, j, temp, start, end; //初始化值 bool isEnd = false; i = 0; start = i; j = nums.Length - 1; end = j; temp = -1; if (nums.Length < k) return -1; //快排思想,但是不用管非目标段的排序 while (!isEnd) { //处理每一段的排序,将比参考值小的往前靠,比参考值大的往后靠,参考值放中间 temp = start; while (i != j) { while (nums[j] <= nums[temp] && j != i) { j--;//在右边找一个比参考值小的 } while (nums[i] >= nums[temp] && i != j) { i++;//在左边找一个比参考值大的 } if (i == j) { //两哨兵相遇,与参考值调换位置 if (i != temp)//注意这两个相等的时候,这种交换就把值变成0了 { nums[i] = nums[i] + nums[temp]; nums[temp] = nums[i] - nums[temp]; nums[i] = nums[i] - nums[temp]; } temp = i; } else { //交换两个找到的值 nums[i] = nums[i] + nums[j]; nums[j] = nums[i] - nums[j]; nums[i] = nums[i] - nums[j]; } } //判断是否找到了,参考的位置就是该数据的真实排名了 if (temp + 1 == k) { isEnd = true; break; } if (temp + 1 < k) { //去右边 j = end; start = temp + 1; i = temp + 1; } else { i = start; end = temp - 1; j = temp - 1; } } return nums[temp]; }
原来这叫Quick Select,和快排是同一个人提出的。
注释已经写得很明白了 也可以参考 快速排序-不用List速排序-不Lis