二插堆的基本原理以及简单实现

六轴机器人轨迹规划之空间直线插补 1.原理简述 直线插补时,指定起止坐标与速度。 确定要插直线的周期增量,分解到xyz轴。 2.matlab代码 clear; clc; p0=[1,2,3]; pf=[2,4,5]; %指定起止位置 v=0.1; %指定速度 x=[p0(1)];y=[p0(2)];z=[p0(3)]; L=((pf(1)-p0(1))^2+(pf(2)-p0(2)... 阅读详情

堆(Heap)

一、堆的基本概念

1. 定义

  • 二叉堆是一种完全二叉树,它满足堆属性:
    • 最大堆:每个节点的值都大于或等于其子节点的值
    • 最小堆:每个节点的值都小于或等于其子节点的值

2. 特点

  • 二、二叉堆的特点

    1. 完全二叉树:除了最后一层,其他层都是满的,最后一层从左到右填充
    2. 堆属性:父节点和子节点之间保持特定的大小关系
    3. 数组表示:可以用数组高效存储,不需要指针

二、堆的数组表示

对于下标为 i 的节点:

  • 父节点:parent(i) = (i-1)/2
  • 左子节点:left(i) = 2*i + 1
  • 右子节点:right(i) = 2*i + 2

堆的相关操作

创建堆的类型

  1. 包括堆的数组

  2. 堆的类型(最大堆,最小堆)

  3. 获取节点的父节点,左孩子,右孩子

class Heap {
public: 
    vector<int> heap; 
    bool isMaxHeap;      // true表示最大堆, false表示最小堆
  	// 获取父节点索引
    int parent(int index) {
        return (index - 1) / 2; 
    } 

    // 获取左孩子索引
    int leftChild(int index) {
        return 2 * index + 1; 
    } 

    // 获取有孩子索引
    int rightChild(int index) {
        return 2 * index + 2; 
    } 
}; 

上浮(Heapify Up)

  1. 上浮操作用于在堆中插入新元素后,恢复堆的性质。

  2. 当我们向堆的末尾添加一个新元素时,可能会破坏堆的堆序性(父节点大于/小于子节点)。

  3. 上浮操作通过不断比较新元素与其父节点,必要时交换它们,直到堆性质恢复。

void heapifyUp(int index) {
    while (index > 0) {
        int parent = (index - 1) / 2;
        // 最大堆:如果当前节点大于父节点,交换
        // 最小堆:如果当前节点小于父节点,交换
        if (compare(heap[index], heap[parent])) {
            swap(heap[index], heap[parent]);
            index = parent;
        } else {
            break;
        }
    }
}

下沉(Heapify Down)

  1. 下沉操作用于移除堆顶元素后,恢复堆的性质。

  2. 当我们移除堆顶元素时,通常将最后一个元素移到堆顶,然后通过下沉操作将其调整到合适位置,恢复堆性质。

void heapifyDown(int index) {
    int size = heap.size();
    while (true) {
        int leftChild = 2 * index + 1;
        int rightChild = 2 * index + 2;
        int target = index;

        // 找到需要交换的子节点
        if (leftChild < size && compare(heap[leftChild], heap[target])) {
            target = leftChild;
        }
        if (rightChild < size && compare(heap[rightChild], heap[target])) {
            target = rightChild;
        }
        
        // 如果需要交换,继续下沉
        if (target != index) {
            swap(heap[index], heap[target]);
            index = target;
        } else {
            break;  // 堆性质已满足
        }
    }
}

插入操作

  1. 插入操作向堆中添加新元素。首先将元素添加到数组末尾.
  2. 然后执行上浮操作将其调整到正确位置。
// 插入元素
    void push(int value) {
        heap.push_back(value); 
        heapifyUp(heap.size() - 1); 
    }  

删除堆顶元素

  1. 检查堆是否为空
  2. 保存堆顶元素
  3. 将最后一个元素移到堆顶
  4. 删除最后一个元素
  5. 如果堆不为空,对堆顶执行下沉操作
   void pop() {
        if (heap.empty()) {
            cout << "堆为空,无法删除!" << endl;
            return;
        }
        heap[0] = heap.back();
        heap.pop_back();
        
        if (!heap.empty()) {
            heapifyDown(0);
        }
    } 

获取堆顶元素

  1. 检查堆是否为空
  2. 返回数组的第一个元素
// 获取堆顶元素
    int top() {
        if (heap.empty()) {
            cout << "堆为空!" << endl;
            return -1;
        }
        return heap[0];
    }

完整代码

class Heap {
public: 
    vector<int> heap; 
    bool isMaxHeap;      // true表示最大堆, false表示最小堆

    // 比较函数
    bool compare(const int& a, const int& b) {
        return isMaxHeap ? a > b : a < b; 
    } 

    // 获取父节点索引
    int parent(int index) {
        return (index - 1) / 2; 
    } 

    // 获取左孩子索引
    int leftChild(int index) {
        return 2 * index + 1; 
    } 

    // 获取有孩子索引
    int rightChild(int index) {
        return 2 * index + 2; 
    } 
 
    // 上浮操作
    void heapifyUp(int index) {
        while (index > 0) {
            int parent = (index - 1) / 2; 
            if (compare(heap[index], heap[parent])) {
                swap(heap[index], heap[parent]); 
                index = parent; 
            } else {
                break; 
            }
        }
    } 

    // 下沉操作
    void heapifyDown(int index) {
        int size = heap.size(); 
        while (true) {
            int leftChild = 2 * index + 1; 
            int rightChild = 2 * index + 2; 
            int target = index; 

            // 找到当前节点、左子节点、右子节点中最符合堆性质的节点
            if (leftChild < size && compare(heap[leftChild], heap[target])) {
                target = leftChild;
            }
            if (rightChild < size && compare(heap[rightChild], heap[target])) {
                target = rightChild;
            }
            
            // 如果当前节点不是最大的/最小的,交换并继续下沉
            if (target != index) {
                swap(heap[index], heap[target]);
                index = target;
            } else {
                break;
            }
        } 
    } 

    // 构造函数 
    Heap(bool maxHeap = true) : isMaxHeap(maxHeap) {} 


    // 从数组建堆的构造函数
    Heap(const vector<int>& arr, bool maxHeap = true) : isMaxHeap(maxHeap) {
        heap = arr;
        // 从最后一个非叶子节点开始建堆
        for (int i = heap.size() / 2 - 1; i >= 0; i--) {
            heapifyDown(i);
        }
    } 

    // 插入元素
    void push(int value) {
        heap.push_back(value); 
        heapifyUp(heap.size() - 1); 
    }  

    // 删除堆顶元素
    void pop() {
        if (heap.empty()) {
            cout << "堆为空,无法删除!" << endl;
            return;
        }
        heap[0] = heap.back();
        heap.pop_back();
        
        if (!heap.empty()) {
            heapifyDown(0);
        }
    } 

    // 获取堆顶元素
    int top() {
        if (heap.empty()) {
            cout << "堆为空!" << endl;
            return -1;
        }
        return heap[0];
    }
    
    // 堆是否为空
    bool empty() {
        return heap.empty();
    }
    
    // 获取堆大小
    int size() {
        return heap.size();
    }
    
    // 获取堆类型
    string getType() {
        return isMaxHeap ? "最大堆" : "最小堆";
    }

}; 
Android16 动态隐藏systemUI右侧音量条 本文介绍了如何屏蔽SystemUI系统音量条并显示自定义音量控制条的实现方法。主要通过两个步骤:1)在编译脚本中定义控制属性persist.rp.show.volume.dialog=off来隐藏系统音量条;2)修改SystemUI源码中的VolumeDialogImpl.java文件,在showH方法中根据属性值判断是否显示系统音量条。当属性值为off时直接return,从而屏蔽系统音量条的显示,实现自定义音量控制条的替代显示。该方法通过系统属性控制显示状态,具有灵活可控的特点。 阅读详情

相关推荐

现代密码学5.3--Hash and MAC

现代密码学5.3--Hash and MAC 博主正在学习INTRODUCTION TO MODERN CRYPTOGRAPHY (Second Edition) --Jonathan Katz, Yehuda Lindell,做一些笔记供自己回忆,如有错误请指正。整理成一个系列现代密码学,方便检索。 第二章定义了完美安全及其对应的密码方案“一次一密”, 第三章介绍了多种安全定义 3.1-3.3 计算安全,PRG和基于PRG构造的满足计算安全的密码方案; 3.4-3.5 CPA安全,PRF和基于PRF构

qq_41545715的博客 681

堆的实现以及利用堆进行排序

堆是一种特殊的完全二叉树,分为最大堆和最小堆。在最小堆中,父节点的值总是小于或等于其子节点的值。这种特性使得堆的根节点始终是所有节点中的最小值,非常适合实现优先队列。堆中某个结点的值总是不⼤于或不⼩于其⽗结点的值;堆总是⼀棵完全⼆叉树。⼆叉树性质对于具有 n 个结点的完全⼆叉树,如果按照从上⾄下从左⾄右的数组顺序对所有结点从0 开始编号,则对于序号为 i 的结点有:若 i>0 , i 位置结点的双亲序号: (i-1)/2;i=0 , i 为根结点编号,⽆双亲结点。

zzh_Zao的博客 1830

欧姆龙 CJ1W-SCU模块使用通配符+结束码实现非固定长度数据的接收

实验设备:CJ2M-CPU33、CJ1W-SCU21、XW2Z-200T 实验目的:了解 CJ1W-SCU 通配符使用 1.硬件接线: CJ1W-SCU21单元号拨码置于8,使用串口1(232口)。 2.软件设置: ① 新建工程,选择PLC型号CJ2M-CPU33,切换到编程模式,如下图: 、 ② 创建I/O并进行相关配置,如下图: ③ 设置为用户设置,协议宏模式,8位数据位,2位停止位,偶校验9600波特率,如下图: 、 ④ 打开CX-Protocal软件,新建工程: .

weixin_42118352的博客 1977

堆的实现详解

堆的实现以及top-k问题

weixin_70238476的博客 2714

HDRnet——双边滤波和仿射变换的摇身一变

layer层数越多,下采样得到的图越小,low-level features的好处是最后的grid会更coarser,最后的特征图的感受野也越多,非线性更好,表达力更强。所以最终grid是5维的[B,in*out,n,H,W],permute之后是[B,H,W,n,in*out],B是batchsize,n表示对guide的量化级数,in*out表示每个cell的变换系数。这部分的处理对象是低分辨率图,利用CNN进行特征提取(局部和全局),最后fuse得到grid,这里面包含了变换的系数。

zcg1942的博客 1568

Tessy学习系列(三):单元测试——官方例程isValueInRange

注意:工程名称以及路劲不能包含空格和中文

不吃鱼的猫的博客 2330

Mockito原理剖析——基本原理、@Spy、@Mock、插桩顺序

文章目录Mock的基本原理Mock和Spy区别调用方法的行为使用场景实例Stubbing插桩顺序的问题插桩先行插桩后行总结Reference Mock的基本原理 通过生成子类的方式,拦截具体的方法调用,将方法调用转发至Mock的桩代码,从而实现方法返回值或者方法执行体的自定义。 Mock和Spy 区别 Mock和Spy的基本区别——在没有进行任何方法调用Mock的情况下,Mock根据全局配置根据方法调用返回值类型返回一个默认值,不会进行具体的方法调用;而Spy对象会默认调用真实的方法。 调用方法的行为

lidelin10的博客 4241

一文吃透 BMS:动力电池与储能共用的电池管控全架构详解

BMS作为电池系统的核心控制器,其技术深度和系统复杂性不容小觑。动力电池与储能系统虽然应用场景不同,但在核心架构上共享大量基础技术。成功的BMS设计需要在精度、可靠性、成本、功耗之间找到最佳平衡点。未来,随着电池技术的进步和智能化需求的提升,BMS将向着更高集成度、更强智能化、更优经济性的方向发展。无论是汽车工程师还是储能系统设计师,深入理解BMS的全栈架构,掌握其核心技术原理,都将是应对未来能源存储挑战的关键能力。核心要点回顾BMS采用分层分布式架构,硬件是基础,算法是灵魂。

小帽子的博客 333

【数据结构】 堆的简单理解和代码实现

前言:本章将详细介绍堆,并通过代码创建堆、实现一些堆的基本操作,最后以TopK问题为文章结尾。 By the way,咱们数据结构中的堆是一种数据结构,堆必然是完全二叉树,而系统层的堆是操作系统中管理内存的一块区域分段,注意区分开。 文章目录1.堆的概念、性质什么是堆:堆的性质:2.堆的代码实现和基本操作定义堆堆的向上调整堆的向下调整堆的初始化堆的销毁堆的插入操作堆的删除操作获取堆顶的元素堆的判空堆内元素数量打印堆内元素3.TopK问题(即在N个数当中,选出最大/小的K个元素)4.源码链接 1.堆的概念

林慢慢的博客 2728

别再死记硬背了!用Python+Matlab/Simulink手把手带你理解PID控制器的‘稳、快、准’

本文通过Python编程和Matlab/Simulink仿真,深入解析PID控制器的‘稳、快、准’三大核心指标,帮助读者直观理解PID控制的实现原理与参数整定技巧。内容涵盖经典控制理论和自动控制原理,提供实战案例和高级调参技巧,适合工业自动化领域的学习者和工程师。

weixin_42551227的博客 365

Vivado+VCS+Verdi三件套实战:如何高效仿真AXI VIP并快速查看波形

本文详细介绍了如何利用Vivado+VCS+Verdi工具链高效仿真AXI VIP并快速查看波形。通过环境配置、Vivado工程准备、VCS编译与仿真优化以及Verdi波形分析技巧,实现仿真速度的数量级提升,显著提高FPGA开发效率。

red88的博客 994

【电机绘图】:插补算法(一)—直线插补—逐点比较法

介绍插补算法的基础,直线的插补,逐点比较法的学习,本文提供直线插补的概念基础,基本思路分析,C语言实现等,代码会直接贴出!

NULL指向我的博客 2万+

SolidWorks速成教程P4-4【装配体 | 第四节】——装配体内修改模型&编辑配合方法&配合报错的解决方法

截止目前已介绍完 SolidWorks装配体的常用功能,但基础薄弱的小伙伴或许对装配体的各类功能还不够熟悉。所以这节将进一步加强装配体的学习,同时介绍新手容易犯的错误。总结出三点,一是装配体内修改模型,二是编辑配合,三是配合报错的解决方法。

嵌入式阿齐Archie 5526

基于双线性内插的DEM高程点内插实现

针对tif格式DEM数据,由于其数据组成为等间距横向和纵向分布的离散高程点构成,可以看做为普通影像的像素值,点与点之间间距为一个像素,那么对DEM数据的内插,就可以当做在每个像素内均匀增加点,每个点的高程值则由周围四个点通过双线性内插计算结果来确定。 假设当点P(x,y)位于P1(x1,y1)、P2(x2,y2)、P3(x3,y3)和P4(x4,y4)四个点构成的矩阵内,如图所示: 设定四个点高程值为p1、p2、p3、p4,中间P点高程为p,P点高程通过P1-P4四个点高程进行拟合。这里采用距离加权

jameschen9051的博客 4658

lwip-2.0.3

lwip是瑞典计算机科学院(SICS)的Adam Dunkels 开发的一个小型开源的TCP/IP协议栈。实现的重点是在保持TCP协议主要功能的基础上减少对RAM 的占用。

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

堆的c语言实现以及简单应用

前言:(废话~😢) 嘿嘿,大家好啊,首先,非常感谢您能抽出宝贵时间来看我的文章,虽然你在看这句的时候已经在浪费了...┭┮﹏┭┮ 啊不是,欸嘿(●'◡'●)。 总之,堆是数据结构中我们接触二叉树遇到的第一个比较强劲的对手呢!哼哼<(  ̄^ ̄)( 所以,来和我一起,打败他,从这位身上吸取宝贵的经验吧~~ 一、堆的认知: 既然要打败对手,那么关于它的认知是必不可少的!它是一个完全二叉树,关于二叉树以及树的介绍可以查询相关资料哦~这里我只介绍几种和堆相关的嘻嘻~😛。 注意,这里代码实现的时候.

QiHai的博客 1939

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

堆的简单实现,堆排序,TopK问题

堆的简单实现以及堆排序。

2301_77438812的博客 1301

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

堆的数组实现

用数组实现堆

2302_76314368的博客 1523

FIR内插滤波器结构与代码实现

信号处理的应用中,有时需要将某个抽样信号变换成一个新的、具有不同抽样率的抽样信号,这就是多抽样速率信号处理。实现抽样率提高的过程被称为内插,实现抽样率降低的过程被称为抽取。由于抽取时内插的对偶系统,因此我们只要对内插滤波器的设计方法有了一定的了解就可以很快的得出抽取滤波器的设计方法。 在这里我们先对FIR内插滤波器的结构进行简单的分析,并对自己设计时采用的滤波器进行介绍。 一、直接结构 直接结构就是按照信号流程直接实现的结构,也是最简单的实现结构。 图中R为抽样率提高的倍数,被称为内插因子,即为补零的过程

daijingxin的博客 6858

【数据结构】堆的实现(简单易懂,超级详细!!!)

堆(heap)是计算机科学中一类特殊的数据结构的统称。堆通常是一个可以被看做一棵树的数组对象。本文从堆的概念和规律,到堆的实现,向下调整算法,建堆,向上调整算法等等,详细讲解,图文并茂!

m0_65679465的博客 7304

堆的实现(偷懒版)

在上期内容介绍了二叉树、还简单提了一下堆的概念和大堆、小堆。回顾一下堆是首先是完全二叉树,因为是完全二叉树所以使用数组储存比较合理。本节重点堆的向上、向下调整算法的代码实现 和 复杂度计算。

2302_80867815的博客 1139

java 最小堆_Java实现最小堆二

Java实现最小堆二如何建立这个堆呢,可以从空的堆开始,然后依次往堆中插入每一个元素,直到所有数都被插入。因为插入第N个元素的所用的时间是O(logN),所以插入所有元素的整体时间复杂度是O(NlogN),代码如下。n=0;for(i=1;i<=m;i++){n++;h[n]=a[i]; //或者写成scanf("%d",&h[n]);siftup();}其实我们还有更快得方法来建...

weixin_39763033的博客 451

堆的性质、堆的实现、堆排序

目录 一、堆的性质 二、堆的实现 1. 存储方式 2. 向堆中插入元素 3. 删除堆顶元素 4. 其他操作 5. 完整代码 三、堆排序 1. 原地建堆 2. 排序 3. 完整代码 4. 建堆的复杂度:O(n) 5. 堆排序的复杂度:O(nlogn) 6. 和快速排序的比较 一、堆的性质 堆是一种特殊的树。 只要满足以下两点,它就是一个堆: 堆是一个完全二叉树; 堆中每一个节点的值都必须大于等于(或小于等于)其子树中每个节点的值。 第一点,堆必须是一个完全二叉树。完全二.

马小超 5627

用python实现CNC插补

1.项目平台 本项目基于python平台设计,适用于python3.6及以上的版本。该项目主要调用了python内置的GUI模块Tkinter,并在其中内嵌了python的海龟绘图(TurtleGraphics)。其主要借鉴的是海龟绘图中的turtle.RawTurtle模块,其特点是轻量化且能嵌入Tkinter中。 2.项目主要功能 该项目主要针对数控机床CNC中的插补算法进行模拟,并对课本中仅...

Love for DeepLearning 4125

堆的实现

堆 的讲解与实现

shylyly_的博客 948

堆的简单实现

关于堆不做过多介绍 堆就是儿子的值一定不小于父亲的值并且树的节点都是按照从上到下,从左到右紧凑排列的树。 (本文为二叉堆) 具体实现并不需要指针二叉树,用数组储存并且利用公式找到父子即可。 父:(i-1)/2 子:i*2+1,i*2+2 插入:首先把新数字放到堆的末尾,也就是右下角,然后查看父的数值,需要交换就交换,重复上述操作直到不需交换 删除:把堆的第一个节点赋值为最后一个节点的...

少说,多做。 3457

堆的实现(堆的插入、堆的删除等)超级全

树是一种非线性的数据结构,它是由n(n>=0)个有限结点组成一个具有层次关系的集合。把它叫做树是因为它看起来像一棵倒挂的树,也就是说它是根朝上,而叶朝下的。

萌新xiaoxu的博客 1414
上一篇: 移动应用开发实验室25级期末考核
下一篇: Objective-C学习 块的概念即基本语法
for_ever_love__
博客等级 码龄1年 65粉丝 311原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值