当前位置: 首页 > article >正文

[笔记]数据结构

文章目录

  • 堆排序
  • 215 数组中第k个最大元素

堆排序

堆排序方法对于记录数较少的文件并不值得提倡,但对n较大的文件还是有效
运行时间主要耗费在:

  1. 建立初始堆
  2. 调整建立新堆 反复筛选

筛选算法进行的关键字比较次数至多为: 2 ( k − 1 ) 2(k-1) 2(k1)
最坏情况O(nlogn),仅需一个记录大小供交换用的辅助存储空间

堆采用线性表表示
typedef SqList HeapType;
void HeadAdjust(HeapType &H,int s,int m){
	//已知H.r[s..m]中记录关键字除H.r[s].key之外均满足堆的定义
	//本函数调整H.r[s]的关键字,使H.r[s..m]成为一个大顶堆
	//s最大的非叶子节点 
	rc = H.r[s]; //辅助元素记录最大非叶子节点
	for(j=2*s;j<=m;j*=2){//2*s末尾元素
	//沿key较大的孩子结点向下筛选
		if(j<m && LT(H.r[j].key,H.r[j+1].key))++j;
		//j为key较大的记录的下标
		if(!LT(rc.key,H.r[j].key))break;//叶子节点大于等于非叶子节点,不需要调整(大根堆)
		//需要调整,将叶子节点和非叶子节点【已经记录】交换
		H.r[s]=H.r[j];
		s=j;

	}
	H.r[s]=rc;//插入元素

}//HeadAdjust



void HeadAdjust(int A[],int i,int m){//易懂版本
	A[0]=A[j];
		for(j=2*i;j<=m;j*=2){//2*s末尾元素
	//沿key较大的孩子结点向下筛选
		if(j<m && A[j]<A[j+1])++j;
		//j为key较大的记录的下标
		if(A[0]>=A[j])break;//叶子节点大于等于非叶子节点,不需要调整(大根堆)
		//需要调整,将叶子节点和非叶子节点【已经记录】交换
		A[i]=A[j];
		i=j;
	}
	A[i]=A[0];
}
void HeapSort(HeapType &H){
	//对顺序表H进行排序
	for(i=H.length/2;i>0;--i){
		HeapAdjust(H,i,H.length);
		//把H.r[1...H.length]建成大顶堆
	}
	for(i=H.length;i>1;--i){
		swap(H.r[1],H.r[i]);
		//将堆顶记录和当前未经排序子序列Hr[1...i]中
		//最后一个记录相互交换
		HeapAdjust(H,1,i-1);
		//将H.r[1..i-1]重新调整为大顶堆
	}
}//HeapSort
  最大堆:priority_queue<int, vector<int>, less<int>> maxHeap;

   最小堆:priority_queue<int, vector<int>, greater<int>> minHeap;

   如果使用 priority_queue<int> 创建堆,默认创建的是最大堆;

    最小堆会在一些图算法中应用,比如prim,dijkstra算法等,

链接

在这里插入图片描述

class Solution {
public:
    int mySqrt(int x) {
        if(x<=1)return x;
        int left=1,right=x/2;
        while(true){
            int mid = (left+right)/2;
          if(mid>0&&mid>x/mid)
            right=mid-1;
          else if((mid+1)>x/(mid+1))
            return mid;
          else 
            left=mid+1;  
        }
    }
};

215 数组中第k个最大元素

在这里插入图片描述
方法一:利用快速排序进行划分

class Solution {
public:
    int findKthLargest(vector<int>& nums, int k) {
    
       return divide(nums,0,nums.size()-1,nums.size()-k);
       
    }

    int divide(vector<int>& nums,int left,int right,int k){
      if(left==right)return nums[k];
      int partition = nums[left],i=left-1,j=right+1;
      while(i<j){
        while(nums[++i]<partition);
        while(nums[--j]>partition);
        if(i<j)swap(nums[i],nums[j]);
      }
      if(k<=j)return divide(nums,left,j,k);
      else return divide(nums,j+1,right,k);
        
    }
};




http://www.kler.cn/a/320878.html

相关文章:

  • 【Linux庖丁解牛】—Linux基本指令(下)!
  • WebSocket协议在Java中的整合
  • 基于Java Web 的家乡特色菜推荐系统
  • java 数组 拼接 详解
  • VSCode设置
  • 什么是MySQL,有什么特点
  • selenium模块的基本使用
  • 【Elasticsearch系列廿二】特殊参数
  • 【openwrt-21.02】openwrt PPTP Passthrough 不生效问题解决方案
  • Delphi5利用DLL实现窗体的重用
  • Vue 响应式监听 Watch 最佳实践
  • C++:STL详解(二)string类的模拟实现
  • 《python语言程序设计》2018版第8章18题几何circle2D类(下部)
  • 2024准备去面试软件测试岗,高频面试题预测?
  • yarn : 无法加载文件 C:\Users\Rog\AppData\Roaming\npm\yarn.ps1,因为在此系统上禁止运行脚本
  • 深入浅出 AbstractQueuedSynchronizer (AQS)
  • SpringCloudEureka简介
  • Qt | linux+openCV+Qt6.5.3环境搭建成功版(带例子)
  • 网络高级day03(Http)
  • 短信视频评论dy版提取,免COOKIE 手机版本介绍说明
  • 前端中CSS选择器权重的问题
  • AccessClient在MacOS14 (sonoma)闪退无法调用远程桌面
  • Ubuntu上如何优雅下载huggingface上某个gguf模型文件
  • 【HarmonyOS鸿蒙应用开发者高级认证争议题】以下关于Taskpool和Worker的描述正确的是
  • 突发,OpenAI CTO离职
  • k8s的一些命令