【数据结构】图论(图的储存方式,图的遍历算法DFS和BFS、图的遍历算法的应用、图的连通性问题)

目录

  • 图论
    • 一、 图的基本概念和术语
    • 二、图的存储结构
      • 1. 数组(邻接矩阵)存储表示
        • 无向图的数组(邻接矩阵)存储表示
        • 有向图的数组(邻接矩阵)存储表示
      • 邻接表存储表示
      • 有向图的十字链表存储表示
      • 无向图的邻接多重表存储表示
    • 三、图的遍历算法
      • 图的遍历——深度优先搜索(DFS)
      • 图的遍历——广度优先搜索(BFS)
    • 四、图的遍历算法的应用(无向图)
    • 五、图的连通性问题
      • 生成树
      • Prim算法
      • Kruskal 算法

图论

一、 图的基本概念和术语

网状结构,逻辑关系多对多

  1. :图G由集合V和E组成,记为G=(V,E)。图中的结点称为顶点,V(G)是顶点的非空有穷集;相关的顶点偶对称为边,E(G)是边的有穷集。

图分为有向图、无向图

  1. 有向图(Digraph)——V(G)是顶点的非空有限集;E(G)是有向边(即弧)的有限集合,弧是顶点的有序对,记<v, w>,v为弧尾(Tail),w为弧头(Head)
  2. 无向图(Undigraph)——V(G)是顶点的非空有限集;E(G)是边的有限集合,边是顶点的无序对,记(v, w)或(w, v),并且(v, w)=(w, v).
    在这里插入图片描述
  1. 顶点:表示数据元素

  2. :表示数据元素之间的逻辑关系,分为有向边(顶点的有序对)和无向边(顶点的无序对)

  3. :边带权的无向图称作无向网;弧带权的有向图称作有向网。

  4. 完全图:n个顶点的含有 n(n-1)/2 条边的无向图称作完全图;n个顶点的含有 e=n(n-1) 条弧的有向图称作 有向完全图.
    若边或弧的个数 e<nlogn,则称作稀疏图,否则称作稠密图。

  5. 邻接点、关联:假若顶点v 和顶点w 之间存在一条边,则称顶点v 和w 互为邻接点,边(v,w)和顶点v 和w相关联

  6. :无向图中和顶点v 关联的边的数目定义为v的度,记为TD(v)
    有向图顶点的度分为入度出度
    入度:有向图中以顶点v为弧头的弧的数目称为顶点v的入度,记为ID(v)
    出度:有向图中以顶点v为弧尾的弧的数目称为顶点v的出
    度,记为OD(v)

  7. 路径、路径长度:设无向图G=(V,E)中的一个顶点序列 u = v i , 0 , v i , 1 , … , v i , m = w { u=v_i,₀,v_i,₁, …, v_i, m=w} u=vi,0,vi,1,,vi,m=w中,若 ( v i , j − 1 , v i , j ) ∈ E , 1 ≤ j ≤ m (v_{i, j-1},v_{i, j})∈E,1 ≤ j ≤ m (vi,j1,vi,j)E1jm,则称从顶点u 到顶点w 之间存在一条路径;路径上边的数目称作路径长度
    简单路径:序列中顶点不重复出现的路径
    简单回路:序列中第一个顶点和最后一个顶点相同的路径

  8. 连通图:若无向图G中任意两个顶点之间都有路径相通,则称此图为连通图。

  9. 连通分量:若无向图为非连通图,则图中各个极大连通子图称作此图的连通分量。

在这里插入图片描述

  1. 强连通图:有向图中若任意两个顶点之间都存在一条有向路径,则称此有向图为强连通图。否则,其各个极大强连通子图称作它的强连通分量。
    在这里插入图片描述

  2. 生成树:假设一个连通图有 n 个顶点和 e 条边,其中 n-1 条边和 n 个顶点构成一个极小连通子图,称该极小连通子图为此连通图的生成树。

  3. 生成森林:对非连通图,则称由各个连通分量的生成树的集合为此非连通图的生成森林。
    在这里插入图片描述

  4. 有向树:如果一个有向图恰有1个顶点的入度为0,其余的顶点入度均为1,则称该图为一棵有向树

  1. 对于非强连通图的一个强连通分量:包含其全部n个顶点、n-1条弧、且只有1个顶点的入度为0、其余的顶点入度均为1的子图称为该连通分量的有生成向树.
  2. 对于非强连通图的所有强连通分量的有向生成树构成该有向图的生成森林.
  3. 一个有向图的生成森林由若干棵有向树组成,含有图中全部顶点,但只有足以构成若干棵不相交的有向树的弧.

二、图的存储结构

■ 图的存储表示(非顺序存储映像):

  1. 图的数组(邻接矩阵)存储表示
  2. 图的邻接表存储表示
  3. 有向图的十字链表存储表示
  4. 无向图的邻接多重表存储表示

■ 设计图的存储表示,应考虑方便以下操作:
• 求入度,出度
• 求邻接顶点
• 判断顶点之间是否有边相连

1. 数组(邻接矩阵)存储表示

无向图的数组(邻接矩阵)存储表示

■ n个顶点的图用2个数组存放:二维数组( n ∗ n n*n nn的矩阵)存放顶点之间的逻辑关系(图中的边、弧),一维数组存放顶点信息(数据元素的
■ 设无向图 G = ( V , E ) G=(V,E) G=(V,E),A[i][j]表示顶点 v i v_i vi v j v_j vj之间是否存在连边
在这里插入图片描述
可以利用对称阵的压缩存储方法存储

无向图顶点 v i v_i vi的度
在这里插入图片描述

有向图的数组(邻接矩阵)存储表示

设有向图 G = ( V , E ) G=(V,E) G=(V,E), A[i][j]表示是否存在顶点 v i v_i vi流向顶点 v j v_j vj的弧.
在这里插入图片描述

有向图邻接矩阵不一定是对称阵
在这里插入图片描述

无向网的邻接矩阵 w i j w_{ij} wij表示在顶点 v i v_i vi v j v_j vj的连边上的权值。 在这里插入图片描述
有时:也用 ∞ ∞ 代表没有边

有向网的邻接矩阵 w i j w_{ij} wij表示在顶点 v i v_i vi流向顶点 v j v_j vj的弧上的权值. 在这里插入图片描述

#define MAXSIZE 100
typedef struct {
	VertexType    vexs[MAXSIZE]; //一维数组存放顶点信息 
	int  arcs[MAXSIZE][MAXSIZE];//邻接矩阵
	int  vexnum, arcnum; //顶点数和边数
	int kind; //图的类型:有向图还是无向图
} MGraph;
MGraph T;

在这里插入图片描述

邻接表存储表示

无向图的邻接表:为顶点vi所建的单链表是将与顶点vi相关联 的边建成一个单链表;或者说:将顶点vi的邻接点建成一个单链表。

■ 图的一种链式存储结构,对图中每个顶点建立一个单链表,为顶
v i v_i vi所建的单链表是将与顶点 v i v_i vi相关联的边或弧建成一个单链表。
■ 用一维数组存放每个顶点的信息和相应单链表的头指针。
■ 每个数组元素存放图中一个顶点:顶点的数据(data)和为其所建单链表的头指针(firstarc)。

在这里插入图片描述

为便于维护数据的一致性,通常单链表中只要给出邻接点的存放位置----在一维数组中对应数组元素的下标即可

存的边数是2e个 ,也就是每个弧存了2次
在这里插入图片描述
有向图的邻接表:第i个单链表(为 v i v_i vi所建单链表)中的结点是从顶点 v i v_i vi流出的弧流向的顶点
顶点vi的出度是第i个单链表中含有的数据元素的个数,即为vi所建单链表的长度。
在有向图的邻接表中不易找到指向该顶点的弧。
在这里插入图片描述

typedef struct ArcNode {
	int vex;  // 该弧所指向的顶点的位置 
	struct ArcNode *link; // 指向下一条弧的指针 
	InfoType  *info;  // 该弧相关信息的指针
}ArcNode;//单链表节点类型

typedef struct VNode {
	int data; // 顶点信息
	ArcNode *firstarc; // 指向第一条依附该顶点的弧
}VNode;//数组元素类型

typedef struct {
	VNode  arc[MAXSIZE]; 
	int   vexnum, arcnum;
	int  kind; //表示有向图还是无向图
}Graphs;

逆向:
有向图的逆邻接表中,为顶点vi建的单链表示流向该顶点的弧
在这里插入图片描述
在这里插入图片描述

网的邻接表表示
在这里插入图片描述

有向图的十字链表存储表示

每个顶点建2个单链表:流出去的弧建一个单链表,流入的弧建一个单链表。
在这里插入图片描述

typedef structArcBox { // 弧的结构表示
	int tailvex, headvex; 
	InfoType *info;//注意定义的类型
	struct ArcBox *hlink,*tlink;
}ArcBox;

typedef structVexNode { // 顶点的结构表示
	int data;
	ArcBox *firstin,*firstout;
}VexNode;

typedef struct {
	VexNode xlist[MAXSIZE]; // 顶点信息
	int vexnum, arcnum; //有向图的当前顶点数和弧数
}OLGraph;

在这里插入图片描述

无向图的邻接多重表存储表示

在这里插入图片描述

边的结构表示

typedef struct Ebox {
	int   mark;
	int   ivex, jvex;
	struct EBox *ilink, *jlink;
} EBox;

三、图的遍历算法

图的遍历:从图中某个顶点出发访遍图中其余顶
点,并且使图中的每个顶点仅被访问一次的过程

遍历应用举例:

  • 判断图的连通性、
  • 求等价类等
  • 求连通分量
  • 求路径相通

深度优先搜索广度优先搜索

图的遍历——深度优先搜索(DFS)

  1. 图的存储——邻接矩阵和邻接表均可以
  2. 判别图中的顶点v的邻接点是否被访问的方法:
    ⮚ 解决的办法:为每个顶点设立一个“访问标志”,设一维数组visited[ ]
    ① visited[v]=1表示顶点v已经被访问
    ② visited[v]=0表示顶点v尚未被访问
    ③ 初始化时,所有顶点均为未被访问
  • 深度优先搜索生成树:访问时经过的顶点和边构成 的子图
  • 深度优先搜索生成森林:若选用多个出发点做深度优先搜索,会产生多棵深度优先搜索生成树—构成深度优先搜索生成森林.

深度优先搜索遍历连通图的过程类似于树的先根遍历`

深度优先搜索应用
判断无向图是否连通?
若从无向图中任一点出发能访问到图中所
有顶点,则该图为连通图
判断有向图是否强连通?
若从有向图中每一点出发能访问到图中所有顶点,则该图为强连通图.

实现方法:
邻接表为例实现图的深度优先搜索
存储结构为:

typedef struct ArcNode {
	int vex;  // 该弧所指向的顶点的位置 
	struct ArcNode *link; // 指向下一条弧的指针 
	InfoType  *info;  // 该弧相关信息的指针
} ArcNode;//单链表节点类型

typedef struct VNode {
	int data; // 顶点信息
	ArcNode *firstarc; // 指向第一条依附该顶点的弧
} VNode;//数组元素类型

typedef struct {
	VNode  arc[MAXSIZE]; 
	int   vexnum, arcnum;
	int  kind; //表示有向图还是无向图
} Graphs;

DFS实现流程图以及代码:
在这里插入图片描述

typedef struct ArcNode {
	int vex;  // 该弧所指向的顶点的位置 
	struct ArcNode *link; // 指向下一条弧的指针 
	InfoType  *info;  // 该弧相关信息的指针
} ArcNode;//单链表节点类型

typedef struct VNode {
	int data; // 顶点信息
	ArcNode *firstarc; // 指向第一条依附该顶点的弧
} VNode;//数组元素类型

typedef struct {
	VNode  arc[MAXSIZE]; 
	int   vexnum, arcnum;
	int  kind; //表示有向图还是无向图
} Graphs;

//深度优先搜索
void DFSTraverse(Graphs G){
	for(int v=0;v<G.vexnum;++v){
		visited[v]=0;
		for(v=0;v<G.vexnum;++v){
			if(!visited[v])
				DFS(G,v);
		}
	}

}

void DFS(Graphs G,int v){
	printf("%d\t",v);
	visited[v]=1;
	p=G.arc[v].firstarc;
	while(p){
		w=p->vex;
		if(visited[w]==0)
			DFS(G,w);
			p=p->link;
	}
}

在这里插入图片描述

图的遍历——广度优先搜索(BFS)

■ 广度优先搜索生成树:访问时经过的顶点和边构成的子图。
■ 广度优先搜索生成森林:选用多个出发点做广度优先搜索,会产生多棵广度优先搜索生成树—构成广度优先搜索生成森林。
■ 对连通图,从起始点v到其余各顶点必定存在路径。按此路径长度递增次序访问。

在这里插入图片描述

int visited[Max];
void BFSTraverse(Graphs G){   
	for(v=0; v<G.vexnum; ++v) visited[v] = 0;
 	for( v=0; v<G.vexnum; ++v ) 
 	if(!visited[v]) 
 		BFS(G, v);
}

void BFS(Graphs G,int v){
	int Q[MAX],f=0,r=0;
	printf("%d\t",w);
	visited[v]=1;
	Q[r++]=v;
	while(f<r){
		x=Q[f++];
		p=G.arc[x].firstarc;
		while(p){
			w=p->vex;
			if(visited[w]==0){
				visited[w]=1;
				printf("%d\t",w);
				Q[r++]=w;
			}
			p=p->link;
		}
	}
}


最小生成树

四、图的遍历算法的应用(无向图)

(待补充)
求两个点之间的最短路径
求两个顶点之间的简单路径
直接使用深度优先搜索还不太行 需要先处理一下
遍历应用举例:

  • 判断图的连通性、
  • 求等价类等
  • 求连通分量
  • 求路径相通

五、图的连通性问题

生成树的存放方式:

  1. 孩子兄弟表示法
  2. 双亲表示法

⮚ 若从无向图中任一点出发采用深度优先搜索或广度优先搜索能访问到图中所有顶点,则该图为连通图,否则为非连通图

对连通图:深度优先搜索或广度优先搜索访问时经过的顶点和边构成的子图称为深度优先搜索生成树或广度优先搜索生成树

对非连通图:深度优先搜索或广度优先搜索访问时经过的顶点和边构成的子图称为深度优先搜索生成森林或广度优先搜索生成森林

生成树

生成树 子图 连通的子图
■ 生成树:假设一个连通图有 n 个顶点和 e 条边,其中 n-1
条边和 n 个顶点构成一个极小连通子图,称该极小连通子图为此连通图的生成树。

生成森林:对非连通图,则称由各个连通分量的生成树的集合为此非连通图的生成森林。

最小生成树 带权图的生成树上的各边权值之和 称为这棵树的代价。最小代价生成树是各边权值总和最小的生成树

最小生成树的性质(MST性质) 采用深度优先搜索 或 广度优先搜索 求? 不太行

贪心策略 不一定是最优解 但在生成最小生成树的时候 是适用的 Prim普利姆算法 Kruscal算法

具有MST性质 就是最小生成树

MST性质(最小生成树性质): 令G=(V, E,
W)为一个带权连通图,T为G的一生成树。对任一不在T中的边uv,如果将uv加入T中会产生一回路,使得uv是回路中权值最大的边。那么树T具有MST性质。

Prim算法

图采用邻接矩阵邻接表存放均可。下面以邻接矩阵为例实现prim算法

define MAX 100
define MAXEDGE 1000000
typedef struct{
	int arcs[MAX][MAX];
	int vexnum,arcnum;
}AGraphs;

Prim算法代码示例:

define MAX 100
define MAXEDGE 1000000
typedef struct{
	int arcs[MAX][MAX];
	int vexnum,arcnum;
}AGraphs;

typedef struct{
	int adjvex;
	int lowcost;
}EdgeType;
/*

当顶点v尚未加入生成树时,closedge[v]存放的是v与生成树中的顶点相连的最好情况:v与生成树中的顶点的所有连边中权值最小的那条边;closedge[v].adjvex存放的这条权值最小的边的另一个顶点,closedge[v].lowcost存放的这条权值最小的边的权值

如何区分生成树中的顶点和不在生成树中的顶点呢?

closedge[w].lowcost==0表示w已经加入生成树
*/
void prim(AGraphs G,int u){
	int i,j,k;
	EdgeType closedge[MAX];
	for(j=0;j<G.vexnum;j++){	
		closedge[j].adjvex=u;
		closedge[j].lowcost=G.arcs[u][j];
	} 
	closedge[u].lowcost=0;
	for(i=1;i<G.vexnum;i++){ 
		k=minclosedge(closedge); 
		printf("(%d,%d)", closedge[k].adjvex,k);
		closedge[k].lowcost=0; 
		for(j=0;j<G.venum;j++)
			if(G.arcs[k][j]< closedge[j].lowcost){ 
				closedge[j].lowcost= G.arcs[k][j]; 
				closedge[j].adjvex =k;
			}
	}
}

int minclosedge(EdgeType closedge[]){
	int min,j,k; min=MAXEDGE; k=-1;
	for(j=0;j<G.vexnum;j++)
		if(closedge[j]. lowcost !=0&&closedge[j].lowcost<min){
			min=closedge[j]. lowcost; k=j;
		}
	return k;
}
//时间复杂度:O(n2) Prim算法适合于稠密图

问法
最小生成树的求解过程
文字叙述 画表 求解过程
伪码描述(上述程序)

Kruskal 算法

先排序
对所有边按照权值升序排序
从小开始加 只要不产生回路
最后加到 n − 1 n-1 n1
需要 排序(适合于吸收图)

Kruscal算法适合稀疏图,时间复杂度为O(eloge),e为图的边数,因为该算法要对边按照权值排序,(堆、快速。归并)排序算法的平均时间复杂度O(eloge)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/558721.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

FPGA_verilog语法整理

FPGA_verilog语法整理 verilog的逻辑值 verilog的常数表达 位宽中指定常数的宽度&#xff08;表示成二进制数的位数&#xff09;&#xff0c;单引号加表示该常数为几进制的底数符号。 二进制底数符号为b&#xff0c;八进制为 o&#xff0c;十进制为d&#xff0c;十六进制为 h…

递归、搜索与回溯算法——穷举vs暴搜vs深搜

T04BF &#x1f44b;专栏: 算法|JAVA|MySQL|C语言 &#x1faf5; 小比特 大梦想 此篇文章与大家分享递归、搜索与回溯算法关于穷举vs暴搜vs深搜的专题 如果有不足的或者错误的请您指出! 目录 1.全排列1.1解析1.2题解 2.子集2.1解析2.1.1解法12.1.2解法1代码2.1.3解法22.1.4解法…

vscode微博发布案例

样例: CSS代码: * {margin: 0;padding: 0; }ul{list-style: none; }.w {width: 900px;margin: 0 auto; }.controls textarea {width: 878px;height: 100px;resize: none;border-radius: 10px;outline: none;padding-left: 20px;padding-top: 10px;font-size: 18px; }.controls…

yolov8 区域计数

yolov8 区域计数 1. 基础2. 计数功能2.1 计数模块2.2 判断模块 3. 主代码4. 实验结果5. 源码 1. 基础 本项目是在 WindowsYOLOV8环境配置 的基础上实现的&#xff0c;测距原理可见上边文章 2. 计数功能 2.1 计数模块 在指定区域内计数模块 def count_objects_in_region(bo…

Redis: 在项目中的应用

文章目录 一、Redis的共享session应用二、分布式缓存1、缓存2、缓存一致性问题解决方案&#xff08;缓存更新策略&#xff09;&#xff08;1&#xff09;作用&#xff08;2&#xff09;三种策略&#xff08;3&#xff09;主动更新策略&#xff08;数据库、缓存不一致解决方案&a…

SSL证书在HTTP与HTTPS中的角色差异是什么?

在互联网的广泛应用背景下&#xff0c;随着网络攻击和数据泄露事件频发&#xff0c;保障用户的数据安全已成为至关重要的议题。传统的HTTP协议在传输数据时不进行加密处理&#xff0c;导致数据在传输过程中暴露于潜在的窃听和篡改风险中&#xff0c;安全性薄弱。而通过引入SSL/…

【HC32L110】华大低功耗单片机启动文件详解

本文主要记录华大低功耗单片机 HC32L110 的 汇编启动过程&#xff0c;包括startup_hc32l110启动文件详细注释 目录 1.启动文件的作用2.堆栈定义2.1 栈2.2堆 3.向量表4.复位程序5.中断服务程序6.堆栈初始化启动过程详解7.1从0地址开始7.2在Reset_Handler中干了啥&#xff1f; 8.…

危险场景智能运维巡检系统

在石油、天然气、煤炭和化工等行业&#xff0c;特别是在I/IIC级防爆区场景中&#xff0c;存在着诸如易燃、易爆、高温、有毒有害以及粉尘等危险因素。例如&#xff0c;油气转运站、催化裂化装置、煤化工甲醇车间以及制氢站等地点&#xff0c;都面临着这些潜在的危险。传统的人工…

VOJ 网页跳转 题解 STL栈

网页跳转 用例输入 10 VISIT https://www.jisuanke.com/course/476 VISIT https://www.taobao.com/ BACK BACK FORWARD FORWARD BACK VISIT https://www.jisuanke.com/course/429 FORWARD BACK用例输出 https://www.jisuanke.com/course/476 https://www.taobao.com/ https…

echart实现排名列表

function createHorizontalBarChart(chartId, data) {if (typeof echarts undefined) {console.error(请先引入 ECharts 库);return;}// 初始化echarts实例var myChart echarts.init(document.getElementById(chartId));// 对数据按照 value 进行降序排序var sortedData dat…

k8s配置configmap指定到容器的指定文件

我们需要将名称为walletkey.properties的文件做成configmap&#xff0c;然后将walletkey.properties文件单独挂载出来到/data/walletkey.properties&#xff0c;且不能覆盖/data目录&#xff0c;具体如下 1、创建configmap configmap文件内容 其中walletkey.properties: >-引…

课时100:正则表达式_基础实践_基础知识

3.1.1 基础知识 学习目标 这一节&#xff0c;我们从 基础知识、简单实践、小结 三个方面来学习 基础知识 需求 我们之前的一些操作&#xff0c;很大程度上都是基于特定的关键字来进行实践的&#xff0c;尤其是面对一些灵活的场景&#xff0c;我们因为过于限定一些关键字&am…

【配电网故障定位】基于二进制矮猫鼬优化算法的配电网故障定位 33节点配电系统故障定位【Matlab代码#82】

文章目录 【获取资源请见文章第6节&#xff1a;资源获取】1. 配电网故障定位2. 二进制矮猫鼬优化算法3. 算例展示4. 部分代码展示5. 仿真结果展示6. 资源获取 【获取资源请见文章第6节&#xff1a;资源获取】 1. 配电网故障定位 配电系统故障定位&#xff0c;即在配电网络发生…

Tensorflow2.0笔记 - 使用卷积神经网络层做CIFA100数据集训练(类VGG13)

本笔记记录CNN做CIFAR100数据集的训练相关内容&#xff0c;代码中使用了类似VGG13的网络结构&#xff0c;做了两个Sequetial&#xff08;CNN和全连接层&#xff09;&#xff0c;没有用Flatten层而是用reshape操作做CNN和全连接层的中转操作。由于网络层次较深&#xff0c;参数量…

在 Node.js 中配置代理 IP 采集文章

不说废话&#xff0c;直接上代码&#xff1a; const http require(http); const https require(https);// 之后可以使用 http 或 https 模块发起请求&#xff0c;它们将自动使用配置的代理 // 代理ip&#xff1a;https://www.kuaidaili.com/?refrg3jlsko0ymg const proxy …

JavaScript算数运算符

源码 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title> </head> <b…

Bert语言大模型基础

一、Bert整体模型架构 基础架构是transformer的encoder部分&#xff0c;bert使用多个encoder堆叠在一起。 主要分为三个部分&#xff1a;1、输入部分 2、注意力机制 3、前馈神经网络 bertbase使用12层encoder堆叠在一起&#xff0c;6个encoder堆叠在一起组成编码端&#xf…

ZooKeeper设置监听器

ZooKeeper设置监听器&#xff0c;通过getData()/getChildern()/xists()方法。 步骤&#xff1a; 1.创建监听器&#xff1a;创建一个实现Watcher接口的类&#xff0c;实现process()方法。这个方法会在ZooKeeper向客户端发送一个Watcher事件通知的时候被调用。 2.注册监听器&…

【工厂模式】工厂方法模式、抽象工厂模式-简单例子

简单工厂模式&#xff0c;请跳转到我的另一篇博客【工厂模式】简单工厂模式-简单例子-CSDN博客 四、工厂方法模式 &#xff08;1&#xff09;这部分还是不变&#xff0c;创建一个Car接口&#xff0c;和两个实现类。 public interface Car {void name(); }public class WuLing…

深入刨析 mysql 底层索引结构B+树

文章目录 前言一、什么是索引&#xff1f;二、不同索引结构对比2.1 二叉树2.2 平衡二叉树2.3 B-树2.4 B树 三、mysql 的索引3.1 聚簇索引3.2 非聚簇索引 前言 很多人看过mysql索引的介绍&#xff1a;hash表、B-树、B树、聚簇索引、主键索引、唯一索引、辅助索引、二级索引、联…
最新文章