【树与二叉树】二叉树顺序结构实现以及堆的概念及结构--详解介绍

数据结构|C语言版】二叉树 各位小伙伴大家好!上次小编给大家讲解了数据结构中的栈和队列,接下来我们讲解一下二叉树!以上就是小编对二叉树的讲解。如果觉得小编讲的还可以,还请一键三连。互三必回!持续更新中~! 阅读详情

在这里插入图片描述

​📝个人主页:@Sherry的成长之路
🏠学习社区:Sherry的成长之路(个人社区)
📖专栏链接:数据结构
🎯长路漫漫浩浩,万事皆有期待

1. 二叉树顺序结构

普通二叉树是不适合用数组来存储的,因为可能会存在大量的空间浪费。而完全二叉树适合使用顺序结构存储。现实中我们通常把堆(一种二叉树)使用顺序结构的数组来存储。

注意 操作系统数据结构中都有栈和堆的概念,这里的堆和操作系统虚拟进程地址空间中的堆是两回事,一个是数据结构,一个是操作系统中管理内存的一块区域分段。
在这里插入图片描述

2.堆

2.1 堆的概念及结构

2.1.1 概念

堆分为小根堆大根堆,根节点始终小于子节点称为小根堆,相反根节点始终大于子节点则称为大根堆。换句话说,将根节点最大的堆叫做最大堆或大根堆,根节点最小的堆叫做最小堆或小根堆。

▶ 大(根)堆,树中所有父亲都大于或者等于孩子,且大堆的根是最大值;
在这里插入图片描述

▶ 小(根)堆,树中所有父亲都小于或者等于孩子,且小堆的根是最小值;
在这里插入图片描述

2.1.2 堆的性质

▶ 堆中某个节点的值总是不大于或不小于其父节点的值
▶ 堆总是一棵完全二叉树

2.2 堆的概念选择题

1、下列关键字序列为堆的是( )
A. 100, 60, 70, 50, 32, 65
B. 60, 70, 65, 50, 32, 100
C. 65, 100, 70, 32, 50, 60
D. 70, 65, 100, 32, 50, 60
E. 32, 50, 100, 70, 65, 60
F. 50, 100, 70, 65, 60, 32

  • 分析:根据堆的概念分析,A 选项为大根堆;
    在这里插入图片描述

2、已知小根堆为 8, 15, 10, 21, 34, 16, 12,删除关键字 8 之后需重建堆,在此过程中,关键字之间的比较次数是( )
A. 1
B. 2
C. 3
D. 4

  • 分析:此题考查的是建堆的过程,所以选择 C 选项
    在这里插入图片描述

3、一组记录排序码为 (5 11 7 2 3 17),则利用堆排序方法建立的初始堆为( )
A. (11 5 7 2 3 17)
B. (11 5 7 2 17 3)
C. (17 11 7 2 3 5)
D. (17 11 7 5 3 2)
E. (17 7 11 3 5 2)
F. (17 7 11 3 2 5)

  • 分析:此题考查的是堆排序建堆的过程,根据下面堆排序的过程分析,选择 C 选项
    在这里插入图片描述

4、、注,请理解下面堆应用的知识再做。最小堆 [0, 3, 2, 5, 7, 4, 6, 8],在删除堆顶元素0之后,其结果是( )
A. [3,2,5,7,4,6,8]
B. [2,3,5,7,4,6,8]
C. [2,3,4,5,7,8,6]
D. [2,3,4,5,6,7,8]

  • 分析:此题考查的是 Pop 堆顶后,重新建堆的变化,所以选择 C 选项
    在这里插入图片描述

2.3 堆的实现

1、堆向下调整算法
向下调整算法有一个前提:左右子树必须是一个堆 (包括大堆和小堆),才能调整。

现在我们给出一个数组,逻辑上看做一颗完全二叉树。我们通过从根节点开始的向下调整算法可以把它调整成一个小堆。

1.1 建堆
有一个随机值的数组,把它理解成完全二叉树,并模拟成堆 (大堆/小堆)

int array[] = {27, 15, 19, 18, 28, 34, 65, 49, 25, 37}

观察这组数据
根下面的左右子树都是小根堆,其实堆向下调整算法就是针对这种特殊数据结构

1.1.1针对于这种类型的数据应该怎么调堆
思路:从根开始与左右孩子比较,如果孩子比父亲小,则两两交换位置,再继续往下调,直到左右孩子都比父亲大或者调到叶子
在这里插入图片描述

1.1.2 如果不满足左右子树是堆,怎么调整?

int array[] = {27, 37, 28, 18, 19, 34, 65, 25, 49, 15}
根的左右子树 37、28 都不满足:这里的想法就是先让左右子树先满足;而对于左右子树 37、28 来说又需要让 37 先满足;这样依此类推直至满足堆的条件。那干脆就从倒数的第一棵树,也就是倒数的第一个非叶子节点开始调整
在这里插入图片描述

关于堆的实现我们使用标准模块化开发格式进行研究:

Heap.h:存放函数声明、包含其他头文件、定义宏。
Heap.c:书写函数定义,书写函数实现。
test.c:书写程序整体执行逻辑。

①.堆的初始化:

堆的初始化与队列相同,首先判断传入指针非空后,将其置空,并将数据置零即可。

//1、对于HeapCreate函数,结构体不是外面传进来的,而是在函数内部自己malloc空间,再创建的
/* 
HP* HeapCreate(HPDataType* a, int n)
{}
*/
//2、对于HeapInit函数,在外面定义一个结构体,把结构体的地址传进来
void HeapInit(HP* php, HPDataType* a, int n)
{
	assert(php); 
	//malloc空间(当前数组大小一样的空间)
	php->a = (HPDataType*)malloc(sizeof(HPDataType) * n);
	if (php->a == NULL)
	{
		printf("malloc fail\n");
		exit(-1);
	}
	//使用数组初始化
	memcpy(php->a, a, sizeof(HPDataType) * n);
	php->size = n;
	php->capacity = n;
	//建堆 
	int i = 0;
	for (i = (n - 1 - 1) / 2; i >= 0; i--)
	{
		AdjustDown(php->a, n, i);
	}
}

②.堆的插入(向上调整算法):

因为堆的存储在物理层面上数组,但是在逻辑层面上二叉树。并且由于只有小根堆和大根堆,所以在插入数据之后要想保证其仍然是堆,就需要进行适当的调整。

插入时从尾部插入,而是否为堆取决于子节点和父节点的关系,若为小根堆则子节点要比父节点要大否则就需要交换子节点和父节点,大根堆则相反。而这种调整方式就叫做向上调整算法。

执行操作前需进行非空判断,防止堆空指针进行操作。
插入前判断空间是否足以用于此次扩容,若不足则进行扩容,直至满足插入条件后堪称插入操作,这个接口的功能实现也与队列的处理方式基本相同。
与队列的不同点在于,为了保证插入后仍然是堆,需要在插入后使用向上调整算法进行适当的调整

//向上调整算法:
//除了child的数据,前面的数构成堆
void AdjustUp(HPDataType* a, int child)
{
	int parent = (child - 1) / 2;
	while (child > 0)
	//parent>=0  感觉有问题 但可以使用
	{
		if (a[child] > a[parent])
		{
			Swap(&a[child], &a[parent]);
			child = parent;
			parent = (child - 1) / 2;
		}
		else
		{
			break;
		}
	}
}
 
//堆插入:
void HeapPush(HP* php, HPDataType x)
{
	assert(php);

	//空间不够,增容
	if (php->size == php->capacity)
	{
		HPDataType* temp = (HPDataType*)realloc(php->a, php->capacity * 2 * sizeof(HPDataType));
		if (temp == NULL)
		{
			printf("realloc fail\n");
			exit(-1);
		}
		else
		{
			php->a = temp;	
		}
		php->capacity *= 2;
	}
	//将x放在最后
	php->a[php->size] = x;
	php->size++;
	//向上调整
	AdjustUp(php->a, php->size - 1);
}

③.堆的删除(向下调整算法):

堆删除的实质是删除堆顶元素,如果我们直接删除堆顶的元素,再将数据挪动,就会破坏堆的结构,所以这种方法并不可取;于是我们这里采用将堆顶的数据与最后一个数据交换,再删除最后一个数据的方法,这样就实现了堆顶数据的删除。接着我们再调整一下堆顶数据的位置即可。

在这里选择的调整方法是:将根节点与它的孩子中的较小值交换,然后再将交换后的节点作为父节点继续与它的子节点交换,直到该节点小于它的子节点,或者成为叶节点。

注意 使用这个方法有一个前提:根节点的两个子树也得是堆才行。而这种方法就叫做向下调整算法。

执行操作前需进行非空判断,防止对空指针进行操作。
删除过程同样与队列近乎一致,不同点是在删除过后为了保证删除堆顶数据后仍为堆,于是需要使用向下调整算法对删除后的结果进行适当的处理。

//向下调整算法:
//左右子树都是大堆或小堆
void AdjustDown(HPDataType* arr, int n, int parent)
{
	int child = parent * 2 + 1;
	while (child < n)
	{
		//选出左右孩子中大的那一个
		if (child + 1 < n && arr[child] < arr[child + 1])//防止越界 右孩子存在
		//child + 1 < n 放左边 先检查
		{
			child++;//右孩子>左孩子 ++
		}
		if (arr[child] > arr[parent])
		{
			Swap(&arr[child], &arr[parent]);
			parent = child;
			child = parent * 2 + 1;
		}
		else//父亲大于孩子 不用交换了
		{
			break;
		}
	}
}
 
//堆顶数据删除:
void HeapPop(HP* php)
{
	assert(php);
	//没有数据删除就报错
	assert(!HeapEmpty(php));
	//交换首尾
	Swap(&php->a[0], &php->a[php->size-1]);
	php->size--;
	//向下调整
	AdjustDown(php->a, php->size, 0);
}
HPDataType HeapTop(HP* php)
{
	assert(php);
	//没有数据获取就报错
	assert(!HeapEmpty(php));
	return php->a[0];
}
int HeapSize(HP* php)
{
	assert(php);
	return php->size;
}

测试删除接口功能实现:

④.取堆顶数据:

取堆顶数据操作与队列完全相同

HPDataType HeapTop(HP* php)
{
	assert(php);
	//没有数据获取就报错
	assert(!HeapEmpty(php));
	
	return php->a[0];
}

⑤.堆中数据个数:

查看堆中的数据个数操作很简单,在判断传入指针非空后,直接返回 p->size 的值,即堆中保存的数据数量即可。

int HeapSize(HP* php)
{
	assert(php);
	
	return php->size;
}

⑥.堆的判空:

堆的判空操作与队列完全相同

//堆数据判空:
bool HeapEmpty(HP* php)
{
	assert(php);
	
	return php->size == 0;
}

⑦.堆的销毁:

堆的销毁与队列相同

void HeapDestroy(HP* php)
{
	assert(php);
	free(php->a);
	php->a = NULL;
	
	php->size = php->capacity = 0;
}

⑦.堆的打印:

void HeapPrint(HP* php)
{
	assert(php);

	int i = 0;
	for (i = 0; i < php->size; i++)
	{
		printf("%d ", php->a[i]);
	}
	printf("\n");
}

2.4 堆的代码实现

注意

▶ 堆的初始化一般是使用数组进行初始化的

▶ 堆的插入数据不分头插、尾插,将数据插入后,原来堆的属性不变

先放在数组的最后一个位置,再向上调整

▶ 堆的删除数据删除的是堆顶的数据,将数据删除后,原来堆的属性不变

为了效率,将第一个和最后一个元素交换,再减容,然后再调整

Heap.h 用于函数的声明

#pragma once

//头
#include<stdio.h>
#include<assert.h>
#include<stdlib.h>
#include<string.h>
#include<stdbool.h>

typedef int HPDataType;

//C++ -> priority_queue 在C++里用的是优先级队列,其底层就是一个堆
//大堆
typedef struct Heap
{
	HPDataType* a;
	int size;
	int capacity;
}HP;
//函数的声明
//交换
void Swap(HPDataType* px, HPDataType* py);
//向下调整
void AdjustDown(HPDataType* arr, int n, int parent);
//向上调整
void AdjustUp(HPDataType* a, int child);
//使用数组进行初始化
void HeapInit(HP* php, HPDataType* a, int n);
//回收空间
void HeapDestroy(HP* php);
//插入x,保持它继续是堆
void HeapPush(HP* php, HPDataType x); 
//删除堆顶的数据,保持它继续是堆
void HeapPop(HP* php);
//获取堆顶的数据,也就是最值
HPDataType HeapTop(HP* php);
//判空
bool HeapEmpty(HP* php);
//堆的数据个数
int HeapSize(HP* php);
//输出
void HeapPrint(HP* php);

Heap.c 用于函数的定义

#include"Heap.h"


void Swap(HPDataType* px, HPDataType* py)
{
	HPDataType temp = *px;
	*px = *py;
	*py = temp;
}
//左右子树都是大堆或小堆
void AdjustDown(HPDataType* arr, int n, int parent)
{
	int child = parent * 2 + 1;
	while (child < n)
	{
		//选出左右孩子中大的那一个
		if (child + 1 < n && arr[child] < arr[child + 1])//防止越界 右孩子存在
		//child + 1 < n 放左边 先检查
		{
			child++;//右孩子>左孩子 ++
		}
		if (arr[child] > arr[parent])
		{
			Swap(&arr[child], &arr[parent]);
			parent = child;
			child = parent * 2 + 1;
		}
		else//父亲大于孩子 不用交换了
		{
			break;
		}
	}
}
//除了child的数据,前面的数构成堆
void AdjustUp(HPDataType* a, int child)
{
	int parent = (child - 1) / 2;
	while (child > 0)
	//parent>=0  感觉有问题 但可以使用
	{
		if (a[child] > a[parent])
		{
			Swap(&a[child], &a[parent]);
			child = parent;
			parent = (child - 1) / 2;
		}
		else
		{
			break;
		}
	}
}
void HeapPrint(HP* php)
{
	assert(php);

	int i = 0;
	for (i = 0; i < php->size; i++)
	{
		printf("%d ", php->a[i]);
	}
	printf("\n");
}
//1、对于HeapCreate函数,结构体不是外面传进来的,而是在函数内部自己malloc空间,再创建的
/* 
HP* HeapCreate(HPDataType* a, int n)
{}
*/
//2、对于HeapInit函数,在外面定义一个结构体,把结构体的地址传进来
void HeapInit(HP* php, HPDataType* a, int n)
{
	assert(php); 
	//malloc空间(当前数组大小一样的空间)
	php->a = (HPDataType*)malloc(sizeof(HPDataType) * n);
	if (php->a == NULL)
	{
		printf("malloc fail\n");
		exit(-1);
	}
	//使用数组初始化
	memcpy(php->a, a, sizeof(HPDataType) * n);
	php->size = n;
	php->capacity = n;
	//建堆 
	int i = 0;
	for (i = (n - 1 - 1) / 2; i >= 0; i--)
	{
		AdjustDown(php->a, n, i);
	}
}
void HeapDestroy(HP* php)
{
	assert(php);
	free(php->a);
	php->a = NULL;
	php->size = php->capacity = 0;
}
bool HeapEmpty(HP* php)
{
	assert(php);
	return php->size == 0;
}
void HeapPush(HP* php, HPDataType x)
{
	assert(php);

	//空间不够,增容
	if (php->size == php->capacity)
	{
		HPDataType* temp = (HPDataType*)realloc(php->a, php->capacity * 2 * sizeof(HPDataType));
		if (temp == NULL)
		{
			printf("realloc fail\n");
			exit(-1);
		}
		else
		{
			php->a = temp;	
		}
		php->capacity *= 2;
	}
	//将x放在最后
	php->a[php->size] = x;
	php->size++;
	//向上调整
	AdjustUp(php->a, php->size - 1);
}
void HeapPop(HP* php)
{
	assert(php);
	//没有数据删除就报错
	assert(!HeapEmpty(php));
	//交换首尾
	Swap(&php->a[0], &php->a[php->size-1]);
	php->size--;
	//向下调整
	AdjustDown(php->a, php->size, 0);
}
HPDataType HeapTop(HP* php)
{
	assert(php);
	//没有数据获取就报错
	assert(!HeapEmpty(php));
	return php->a[0];
}
int HeapSize(HP* php)
{
	assert(php);
	return php->size;
}

Test.c 用于测试函数

#include"Heap.h"

void TestHeap()
{
	int arr[] = { 27, 37, 28, 18, 19, 34, 65, 25, 49, 15 };
	HP hp;
	HeapInit(&hp, arr, sizeof(arr)/sizeof(arr[0]));
	HeapPrint(&hp);
	HeapPush(&hp, 18);
	HeapPrint(&hp);
	HeapPush(&hp, 98);
	HeapPrint(&hp);
	printf("\n\n");
	//将堆这数据结构实现好后,我们就可以利用这些接口实现排序
	while(!HeapEmpty(&hp))
	{
		printf("%d ", HeapTop(&hp));	
		HeapPop(&hp);
	}
	printf("\n");
	
}
int main()
{
	TestHeap();
	return 0;
}

3.总结:

今天我们认识并学习了二叉树顺序结构的相关概念,并且对堆的概念及结构也有了一定的了解。还对二叉树顺序存储的实例——堆的各接口功能进行了实现。下一篇博客我们将从堆的时间复杂度详解以及堆的应用—堆排序、TOP - K问题进一步介绍堆。希望我的文章和讲解能对大家的学习提供一些帮助。

当然,本文仍有许多不足之处,欢迎各位小伙伴们随时私信交流、批评指正!我们下期见~

在这里插入图片描述

实现顺序结构二叉树”+ 顺序结构二叉树 阅读详情

相关推荐

哈夫曼的构建(详解顺序结构和链式结构

详解哈夫曼的构建,包含顺序结构和链式结构两种方式

CXR_XC的博客 1万+

数据结构初阶】顺序结构二叉树)接口实现详解

1 1.1 的概念结构 1.2 的相关术语 1.3 的表示 1.4 结构实际运用场景 2二叉树 2.1 概念结构 2.2 特殊的二叉树 2.2.1 满二叉树 2.2.2 完全二叉树 2.3 二叉树存储结构 2.3.1 顺序结构 2.3.2 链式结构 3实现顺序结构二叉树(小) 3.1 的概念结构 3.2 实现 3.2.1 的定义 3.2.2 初始化销毁 3.2.3 交换 3.2.4 入向上调整函数 3.2.5 判空顶数据的大小 3.2.6 出向下调整 大

fhvyxyci的博客 2252

【Solidworks学习使用(1)__2022版本保姆级安装方法】

Solidworks 2020安装

coder-kimbell的博客 5983

数据结构-二叉树·顺序结构实现

本篇文章对 的相关概念及结构二叉树的概念结构二叉树顺序结构实现的相关知识详细讲解!二叉树链式结构在下一章讲解!

2301_77509762的博客 2329

数据结构入门指南】二叉树顺序结构: 实现(全程配图,非常经典)

普通的二叉树适合用数组来存储的,因为可能会存在大量的空间浪费。而完全二叉树更适合使用顺序结构存储。现实中我们通常把(一种二叉树)使用顺序结构的数组来存储,需要注意的是这里的和操作系统虚拟进程地址空间中的是两回事,一个是数据结构,一个是操作系统中管理内存的一块区域分段。

Zhenyu_Coder的博客 9419

DS初阶:二叉树顺序结构实现

学会利用实现排序和TOP-K问题

weixin_51142926的博客 8509

数据结构二叉树顺序结构实现

一.二叉树顺序结构普通的二叉树适合用数组来存储的,因为可能会存在大量的空间浪费。而完全二叉树更适合使用顺序结 构存储。现实中我们通常把(一种二叉树)使用顺序结构的数组来存储,需要注意的是这里的和操作系统 虚拟进程地址空间中的是两回事,一个是数据结构,一个是操作系统中管理内存的一块区域分段。二.的概念结构的性质:1.中某个节点的值总是大于或小于其父节点的值;2.总是一棵完全二叉树。三.实现

HEBRE的博客 4007

数据结构初阶】七、非线性表里的二叉树实现 -- C语言顺序结构

非线性表里的二叉树实现 -- C语言顺序结构):1 . 非线性表里的 (Tree) ;2 . 中的 二叉树(Binary Tree) ;3 . 完全二叉树中的 (Heap) ;4 . 实现 ;5 . 对应代码

正在努力学C呀!(要学好久呢......) 4251

二叉树顺序结构的概念及性质(c语言实现

二叉树顺序结构 普通的二叉树适合用数组来存储的,因为可能会存在大量的空间浪费。完全二叉树就比较适合使用顺序结构存储(数组)。现实中我们通常把(一种二叉树)使用顺序结构的数组来存储 注意:此非“彼”——操作系统虚拟进程地址空间中的。二者一个是一个是数据结构,一个是操作系统中管理内存的一块区域 的概念结构 需要满足两点: 1. 是一个完全二叉树,即除了最底层,其他层都是完全填满,最底层从左到右填充 2. 中的每个节点的值都必须大于等于(最大)或小于等于(最小)其子节点的值

qq_74415153的博客 1329

二叉树详解

目录前言一、的概念结构1、的概念2、的表示 3、在实际中的应用(表示文件系统的目录结构)二、二叉树概念及结构1.概念 2、特殊的二叉树3、二叉树的性质4、二叉树的存储4.1顺序存储4.2链状存储 三、二叉树顺序结构实现1、二叉树顺序结构2、的概念结构3、实现3.1的代码框架3.2的插入3.3的删除3.4的建立 3.5建的时间复杂度 4、的应用4.1排序 4.2TOP-K问题四、二叉树链式结构实现 1、建二叉树2、二叉树的遍历2.1前序、中序以及后序遍历2.2层序遍历

weixin_59371851的博客 5万+

数据结构二叉树顺序结构,详细介绍以及实现排序

实现排序,TopK

林宇恒的博客 3080

二叉树介绍及其顺序结构实现

底层的结构·是数组,所以对结构的定义就和顺序表的定义差多int size;//记录有效元素的个数//记录申请的空间容量}Hp;!

2302_79964175的博客 2153

【初阶数据结构算法】初识二叉树的概念以及和完全二叉树之间的关系

在上面的三个示例图中,它们的根节点都是A,然后BCD三个节点分别构成了三课子,BCD可以认为是三颗子的“根节点”,但是它们并非是真正的结构,因为子之间有了交集,满足刚刚讲的的最后一个特点,所以构成真正的结构。⼆叉的链式存储结构是指,⽤链表来表⽰⼀棵⼆叉,即⽤链来指⽰元素的逻辑关系。在中,子之间是独立存在的,互影响,我们只看一颗子的根节点是否是这颗子的最小值,在左子中15是它的最小值,在右子中56是它的最小值,所以它依然满足的定义,因为子之间是独立存在的,互影响。

hdxbufcbjuhg的博客 3954

数据结构顺序结构二叉树】(1)

排序时间复杂度计算。

qq_67578580的博客 1954

数据结构--&二叉树&顺序结构存储的二叉树

1.检查并扩容(如需):若满,则扩容。2.末尾插入:将新元素添加到数组的末尾。3.向上调整:从新元素开始,其父节点比较。若新元素大,则交换位置,并继续向上比较直至需交换或到达根节点。4.更新大小:大小加1。1.检查非空:若为空,则直接返回。2.交换并减小:将末尾元素交换,然后减小大小。3.向下调整:从新的顶开始,其孩子比较并交换(如需),直至性质恢复或到达底。

2403_82706967的博客 2658

数据结构-二叉树_

对于深度为 K 的,有 n 个 结点的⼆叉,当且仅当其每⼀个结点都深度为K的满⼆叉中编号从 1 ⾄ n 的结点⼀⼀对应时称 之为完全⼆叉。孩⼦兄弟表⽰法: 结构相对线性表就⽐较复杂了,要存储表⽰起来就⽐较⿇烦了,既然保存值域,也要保存结点和结 点之间的关系,实际中有很多种表⽰⽅式如:双亲表⽰法,孩⼦表⽰法、孩⼦双亲表⽰法以及孩⼦ 兄弟表⽰法等。在结构中,我们最常⽤的就是⼆叉,⼀棵⼆叉是结点的⼀个有限集合,该集合由⼀个根结点 加上两棵别称为左⼦和右⼦的⼆叉组成或者为空。

wdnmdfky的博客 3470

数据结构顺序结构二叉树(超详解)

的相关概念,向上/向下调整算法顺序结构二叉树实现

egoist2023的博客 2299

数据结构二叉树顺序结构实现及时间复杂度计算(二)

一,二叉树顺序结构实现二叉树顺序结构的概念结构的接口实现的创建接口函数向上调整算法向下调整算法顶元素建的时间复杂度的创建, 向上调整建法向下调整建法,向上调整建的时间复杂度向 下调整建的时间复杂度的应用排序建利用交换删除思想来进行排序TOP-K问题

m0_71676870的博客 3535

leetcode 56合并区间

这道题你可以把它压缩成一个非常好记的思路:先排序,再逐个比较;能合并就扩右边界,能合并就加入答案。具体来说,先用: 把所有区间按照左端点从小到大排序。排序之后,我们只需要拿“当前区间”和 里最后一个已经合并好的区间比较。如果: 说明前一个区间的右端点比当前区间左端点还小,二者没有重叠: 所以直接: 如果满足: 那就说明: 两个区间重叠,例如: 此时左端点用动,只需要把右端点扩大: 所以整道题可以记成: 这道题容易忘的函数/语法 含义:对整个 排序。对于:

qq_63176310的博客 229

【3DSlicer】基于心脏ct影像重建3d模型及导出

软件:3DSlicer4.11 基于心脏ct影像重建3d模型

Liuees的博客 1万+

Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)

Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计),个人经导师指导并认可通过的高分设计项目,评审分99分,代码完整确保可以运行,小白也可以亲自搞定,主要针对计算机相关专业的正在做毕业设计、课设的学生和需要项目实战练习的学习者,可作为毕业设计、课程设计、期末大作业,代码资料完整,下载可用。Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品溯源平台系统项目源码+论文(毕业设计&课程设计)Java基于区块链技术的农产品

上一篇: 【树与二叉树】树与二叉树的概念及结构--详解介绍
下一篇: 【树与二叉树】堆的时间复杂度详解以及堆的应用—堆排序、TOP - K问题
Sherry的成长之路
Sherry的成长之路 CSDN实力新星 CSDN实力新星
博客等级 码龄4年 4983粉丝 · 165原创
评论 20
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Sherry的成长之路

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值