class Solution {
void swap(int[] nums,int i,int j){
int temp=nums[i];
nums[i]=nums[j];
nums[j]=temp;
}
public void heapAdjust(int[] nums,int i,int n){
int temp=nums[i];
//j*2+1去到temp位置的左节点
for(int j=2*i+1;j<n;j=j*2+1){
//如果此时具有右节点,则找到两个节点中更大的一个数
if(j+1<n && nums[j]<nums[j+1])
j++;
//如果此时是大于左右子节点,则跳出循环,已经找到了对应的位置
if(temp>=nums[j])
break;
//大的移到顶点
nums[i]=nums[j];
//记录temp 应该放入的位置此时不交换,可以减少交换次数,前两步我们始终用temp对比所以此时可以不交换,只进行记录
i=j;
}
//i此时就是temp的位置
nums[i]=temp;
}
public int findKthLargest(int[] nums, int k) {
//将数组变成一个大根堆,尽量从最后一个非叶子节点开始,可以降低一定的时间复杂度
for(int i=(nums.length/2-1);i>-1;i--){
//length/2 目的是将所有具有子节点的节点传过去 完全二叉树的非叶子节点数 例如 1,2,3,4 从下标0,1就是非叶子节点
//满足i<nums.length/2
heapAdjust(nums,i,nums.length);
}
//排序过程 i为已经排好的元素个数
for(int i=0;i<nums.length;i++){
//首尾元素交换
swap(nums,0,nums.length-i-1);
//交换后此时需要堆排的数组长度-1
heapAdjust(nums,0,nums.length-i-1);
}
}
}