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

stm32之SPI通信协议

文章目录

  • 前言
  • 一、SPI通信协议
    • 1.1 SPI简介
    • 1.2 SPI通信特点
    • 1.3 SPI与I2C对比
  • 二、SPI硬件电路
  • 三、SPI通信原理
  • 四、SPI时序单元
    • 4.1 起始和终止条件
    • 4.2 交换一个字节(模式1)
    • 4.3 交换一个字节(模式0)
    • 4.4 交换一个字节(模式2和3)
  • 五、SPI时序
    • 5.1 发送指令
    • 5.2 指定地址写
    • 5.3 指定地址读


前言

提示:本文主要用作在学习江科大自化协STM32入门教程后做的归纳总结笔记,旨在学习记录,如有侵权请联系作者

本文主要探讨SPI通信协议。关于SPI通信的内容我主要会分为两大块来讲,第一块,就是介绍协议规则,然后用软件模拟的形式来实现协议。第二块,就是介绍stm32的SPI外设,然后用硬件来实现协议。


一、SPI通信协议

1.1 SPI简介

SPI(Serial Peripheral Interface)是由 Motorola 公司开发的一种通用同步串行数据通信总线。它是一种广泛用于短距离通信的标准接口协议,主要用于微控制器与外设之间的通信,如传感器、显示屏、存储器模块等。

下图所示依次为Flash存储器,型号为W25Q64、OLED显示屏、2.4G无线通信模块,芯片型号为NRF24L01以及Micro SD卡,他们都支持SPI通信协议。

在这里插入图片描述

1.2 SPI通信特点

  • 同步通信: SPI 使用主设备(Master)产生的时钟信号(SCK)来同步数据传输,确保主从设备的数据通信在精确的时钟信号下进行。

  • 全双工通信: SPI 是全双工通信协议,可以同时进行数据的发送和接收。数据在两个方向上通过两条独立的线进行传输,使其能够实现高速通信。

  • 一主多从架构: SPI 通信支持一个主设备(Master)控制多个从设备(Slave)。主设备通过选择特定的从设备来进行通信,每个从设备都需要一个独立的从设备选择线(SS,Slave Select)来激活或禁用该设备。

1.3 SPI与I2C对比

以下是SPI与I2C通信特性的一些对比:

特性SPII2C
通信方式全双工半双工
通信线数4 根 (MOSI, MISO, SCK, SS)2 根 (SDA, SCL)
通信速度高速 (通常可达几 Mbps,部分设备可达几十 Mbps)低速至中速 (通常最高1Mbps,部分设备可达3.4Mbps)
协议复杂性较低,不需要地址解析和握手较高,需要处理器协议的握手、应答信号、地址解析
多设备支持支持,但需要为每个从设备单独配置 SS 线支持,通过 7 位或 10 位地址选择设备
总线长度较短,适合短距离高速通信较长,可支持长距离通信
同步时钟是,由 SCK 线提供是,由 SCL 线提供
硬件开销较高,需要 4 根线,且多个从设备需额外的 SS 线低,只需要 2 根线和上拉电阻
功耗较高,高速通信下功耗会增加较低,适合低功耗应用
主从关系固定的单主多从,主设备控制通信支持多主多从,主从角色可动态切换
可靠性较低,没有应答机制,无法检测从设备错误较高,具有应答机制,检测和处理错误较为简单
实现难度较低,协议简单,实现容易较高,协议复杂,实现较为困难
典型应用ADC、DAC、显示器、闪存、传感器、高速外围设备温度传感器、EEPROM、RTC、低速外围设备

简而言之就是:

I2C 适合多设备通信,低功耗和长距离应用场景,如传感器网络、低速外围设备等。其复杂的协议结构使其在多设备通信时具有优势,但在高速通信场景下,SPI 更为适合。

SPI 适合需要高速、全双工通信的应用场景,适合短距离、高速的数据传输,如存储器模块、显示屏等。虽然它需要更多的通信线和额外的 SS 线来选择从设备,但其简单性和高速性能使其在实时和高吞吐量应用中表现突出。

二、SPI硬件电路

在这里插入图片描述

上图所示为一个典型的SPI应用电路,下面我们来看一下这几根通信线。

  • SCK(Serial Clock): 串行时钟线,由主设备生成的时钟信号,用于同步数据传输。
  • MOSI(Master Output, Slave Input): 主设备输出、从设备输入线,用于主设备向从设备发送数据。
  • MISO(Master Input, Slave Output): 主设备输入、从设备输出线,用于从设备向主设备发送数据。
  • SS(Slave Select): 从设备选择线,由主设备控制,用于选择和激活特定的从设备。通常为低电平有效。

首先,SCK,时钟线。时钟线完全由主机掌控,所以对于主机来说,时钟线为输出,对于所有从机来说,时钟线都为输入,这样主机的同步时钟就能送到各个从机了。然后是MOSI,主机输出从机输入。数据传输方向是,主机通过MOSI输出,所有的从机通过MOSI输入。接着是MISO,主机输入从机输出。数据传输方向是,所有的从机通过MISO输出,主机通过MISO输入。

那到这里,SCK、MOSI、MISO的链接方式我们就清楚了。

为了确定通信的目标,主机需要另外引出多条SS控制线,分别接到各从机的SS引脚,主机的SS线都是输出,从机的SS线都是输入。SS线是低电平有效,主机想指定谁就把对应的SS线输出置低电平就行了。比如,主机初始化之后所有的SS都输出高电平,这样就是谁也不指定。假设主机需要和从机1进行通信,那主机直接将SS1线输出置低电平即可。当主机和从机1通信完成之后再把SS1置回高电平,这样从机1就知道主机结束了和我的通信了。

我们再来看一下SPI的引脚配置:输出引脚配置为推挽输出,输入引脚配置为浮空或上拉输入。

对于输出,我们配置为推挽输出。推挽输出,高低电平均有很强的驱动能力,这将使得SPI引脚信号的上升以及下降沿都非常迅速。得益于推挽输出的驱动能力使得SPI信号变化得很快,那自然它也就能达到更高的传输速度了。一般SPI都能轻松达到MHz的速度级别。

对比于I2C,I2C下降沿非常迅速,但是上升沿就比较缓慢了。I2C并不是不想使用更快的推挽输出,而是I2C要实现半双工,经常需要切换输入输出,而且I2C又要实现多主机的时钟同步和总线仲裁,这些功能都不允许I2C使用推挽输出,要不然一不小心就电源短路了。因此,I2C既然选择了更多的功能那就自然要放弃更强的性能了。

注意:在SPI协议里有一条规定,当从机的SS引脚为高电平也就是从机未被选中时,从机的MISO引脚必须切换为高阻态,高阻态就相当于引脚断开,不输出任何电平。在从机的SS线为低电平时,MISO才允许变为推挽输出。这样就可以防止一条线上有多个输出而导致电平冲突的问题了。

总结一下就是:
- 所有SPI设备的SCK、MOSI、MISO分别连在一起。
- 主机另外引出多条SS控制线,分别接到各从机的SS引脚。
- 输出引脚配置为推挽输出,输入引脚配置为浮空或上拉输入。

三、SPI通信原理

在讲时序单元之前我们先来看一下SPI的移位示意图,它是SPI硬件电路设计的核心,只要你把这个移位示意图搞懂了,那无论是上面的硬件电路还是等会要讲到的软件时序理解起来都会更加轻松。

在这里插入图片描述

SPI的基本收发电路就是使用了这样一个移位的模型。左边是SPI主机,里面有一个8位的移位寄存器,右边是SPI从机,里面也有一个8位的移位寄存器。移位寄存器这里有一个时钟输入端,因为SPI一般都是高位先行的,所以每来一个时钟移位寄存器都会向左进行移位,从机中的移位寄存器也是同理。移位寄存器的时钟源是由主机提供的,这里叫作波特率发生器。它产生的时钟驱动主机的移位寄存器进行移位,同时这个时钟也通过SCK引脚进行输出接到从机的移位寄存器里。

移位寄存器的接法是,主机移位寄存器左边移出去的数据通过MOSI引脚输入到从机移位寄存器的右边,从机移位寄存器左边移出去的数据通过MISO引脚输入到主机移位寄存器的右边,这样组成一个圈。

在这里插入图片描述

接下来我们来分析一下这个电路是如何工作的。

首先,我们规定波特率发生器时钟的上升沿,所有移位寄存器向左移动一位,移出去的位放在引脚上。波特率发生器时钟的下降沿,引脚上的位采样输入到移位寄存器的最低位。现在我们假设主机有个数据10101010要发送到从机,同时,从机也有个数据01010101要发送到主机。

在这里插入图片描述

首先,主机驱动时钟产生一个上升沿,这时移位寄存器中所有的位都向左移动一位,然后从最高位移出去的数据就会被放到通信线上,数据放到通信线上实际上是放到了输出数据寄存器。

在这里插入图片描述

可以看到,此时MOSI的数据是1,所以MOSI的电平就是高电平,MISO的数据是0,所以MISO的电平就是低电平,这就是第一个时钟上升沿执行的结果。

在这里插入图片描述

之后,时钟继续运行,上升沿之后下一个边沿就是下降沿。在下降沿时主机和从机内都会进行数据采样输入。即MOSI的1会采样输入到从机移位寄存器的最低位,MISO的0会采样输入到主机移位寄存器的最低位,这就是第一个时钟结束后的结果。

在这里插入图片描述

那下一个时钟继续运行,下一个上升沿同样的操作,移位输出,随后,下降沿,数据采样输入。如此循环8个时钟即可完成一个字节的数据交换,交换的结果是主机的数据10101010发送到了从机的移位寄存器里,从机的数据01010101发送到了主机的移位寄存器里来,这就实现了主机和从机一个字节数据的交换了。实际上,SPI的运行过程就是这样,SPI的数据收发都是基于字节交换这个基本单元来进行的。

在这里插入图片描述

简而言之就是,SPI通信的基础是交换一个字节,有了交换一个字节就可以实现发送一个字节、接收一个字节以及发送同时接收一个字节这三种功能。

四、SPI时序单元

接下来我们来看一下数据传输的基本时序单元,这个基本时序单元就是建立在我们刚刚讲过的移位模型上的。那么这个基本单元什么时候开始移位?是上升沿移位还是下降沿移位的呢?这些SPI都没有限定死而是给了我们可以配置的选择,这样的话SPI就可以兼容更多的芯片。

SPI有两个可以配置的位,分别叫作 CPOL(Clock Polarity,时钟极性)CPHA(Clock Phase,时钟相位) ,CPOL 和 CPHA 是用于控制SPI总线数据采样和数据发送时序的两个关键配置,这两个参数决定了数据与时钟信号的关系,影响数据的采样和传输时机。

CPOL决定了SPI通信中空闲状态下时钟信号SCK的电平状态。当时钟信号没有进行数据传输时(空闲状态),SCK可以处于高电平或低电平,这由CPOL来决定。当CPOL = 0时,表示为空闲时SCK保持低电平,当CPOL = 1时,表示为空闲时SCK保持高电平。

CPHA决定了数据采样的时机,控制在时钟的哪个边沿进行数据采样。当CPHA = 0时,表示数据在第一个时钟边沿采样,当CPHA = 1时,表示数据在第二个时钟边沿采样。

如下表所示,CPOL和CPHA的不同组合决定了SPI通信的4种模式,每种模式定义了时钟和数据的同步方式。

模式CPOLCPHA时钟空闲时SCK电平SCK第一个边沿SCK第二个边沿
模式000低电平移入数据移出数据
模式101低电平移出数据移入数据
模式210高电平移入数据移出数据
模式311高电平移出数据移入数据

虽然模式有四种,但是它们的功能是一样的,在实际使用中模式0的应用是最多的,其他模式到时候用到了再回来查表就行了。ok,废话不多说,让我们先来看一下第一个基本时序单元吧。

4.1 起始和终止条件

在这里插入图片描述
起始条件:SS从高电平切换到低电平
终止条件:SS从低电平切换到高电平

简而言之就是SS低电平选中从机,然后SS低电平期间表示正在通信,SS高电平结束通信。

4.2 交换一个字节(模式1)

这个时序的基本功能是交换一个字节,接下来我们详细分析一下这个时序。

在这里插入图片描述

CPOL=0:空闲状态时,SCK为低电平。
CPHA=1:SCK第一个边沿移出数据,第二个边沿移入数据。

首先是SS,从机选择。在通信开始前,SS为高电平,在通信过程中SS始终保持为低电平,通信结束SS恢复为高电平。

再来看一下MISO,主机输入从机输出。因为有多个从机输出连接了在一起,如果同时开启输出容易造成冲突。所以我们的解决方案是,在SS未被选中的状态下从机的MISO引脚必须关断输出,即配置输出为高阻状态。那在这里,SS高电平时,MISO用一条中间的线表示为高阻态。SS下降沿之后,从机的MISO被允许开启输出。SS上升沿之后,从机的MISO必须置回高阻态。

接下来我们看一下移位传输的操作。SCK第一个边沿,也就是上升沿,主机和从机同时移出数据,主机通过MOSI移出最高位,此时MOSI的电平就表示了主机要发送数据的B7。从机通过MISO移出最高位,此时MISO的电平表示从机要发送数据的B7。然后时钟运行产生下降沿,此时主机和从机同时移入数据,也就是进行数据采样,主机移出的B7进入从机移位寄存器的最低位,从机移出的B7进入主机移位寄存器的最低位。

这样,一个时钟脉冲产生完毕,一个数据位也就传输完毕了。接下来就是同样的流程重复8次,这样一个字节的数据交换就完成了。如果主机只想交换一个字节,那这时就可以把SS重新置回高电平结束通信了。

4.3 交换一个字节(模式0)

在这里插入图片描述
CPOL=0:空闲状态时,SCK为低电平
CPHA=0:SCK第一个边沿移入数据,第二个边沿移出数据

模式0和模式1的区别,在时序上来看,模式0的数据移出移入的时机会比模式1提前半个时钟,也就是相位提前了。

模式0在SCK第一个边沿就要移入数据,但数据总得先移出再移入对吧?所以在模式0的配置下,SCK在第一个边沿之前就要提前开始移出数据了。所以趁SCK还没有变化,SS下降沿时,就要立刻触发移位输出。所以这里MOSI和MISO的输出是对齐到SS的下降沿的,或者说这里把SS的下降沿也当作时钟的一部分了。那SS下降沿触发了输出,SCK上升沿就可以采样输入数据了,这样B7就传输完毕。之后,SCK下降沿,移出B6,SCK上升沿,移入B6,然后继续,下降沿移出数据,上升沿移入数据,最终在第8个上升沿时B0位移入完毕,整个字节交换完成。

之后,SCK还有一个下降沿,如果主机只需要交换一个字节就结束的话,那在这个下降沿时MOSI可以置回默认电平或者不去管它。MISO也会变化一次,SS上升沿之后,从机的MISO置回高阻态,这就是SPI交换一个字节模式0。

总结一下就是,模式0和模式1的区别就在于,模式0把这个数据变化的时机给提前了。在实际应用中模式0的应用是最多的,所以我们重点掌握模式0即可。

4.4 交换一个字节(模式2和3)

1. 交换一个字节(模式2)

在这里插入图片描述

CPOL=1:空闲状态时,SCK为高电平
CPHA=0:SCK第一个边沿移入数据,第二个边沿移出数据

2. 交换一个字节(模式3)

在这里插入图片描述

CPOL=1:空闲状态时,SCK为高电平
CPHA=1:SCK第一个边沿移出数据,第二个边沿移入数据

五、SPI时序

SPI对字节流功能的规定不像I2C那样,I2C的规定一般是,有效数据流第一个字节是寄存器地址,之后依次是读写的数据,使用的是读写寄存器的模型,而在SPI中通常采用的是指令码加读写数据的模型。这个过程就是,SPI起始后第一个交换发送给从机的数据一般叫作指令码,在从机中对应的会定义一个指令集,当我们需要发送什么指令时就可以在起始后第一个字节发送指令集里面的数据,这样就能指导从机完成相应的功能了。

不同的指令可以有不同的数据个数,有的指令只需要一个字节的指令码就可以完成,比如W25Q64的写使能、写失能等指令。而有的指令后面就需要再跟读写的数据,比如W25Q64的写数据、读数据等。写数据,指令后面就得跟上写入的地址和数据,读数据,指令后面就得跟上读取的地址,这就是指令码加读写数据的模型。

由于每个芯片对SPI时序字节流功能的定义都不一样,在这里我们就以读写W25Q64存储器为例进行讲解。

5.1 发送指令

这个时序的功能是向SS指定的设备发送指令(0x06)

在这里我们使用的是SPI的模式0,模式0的规定是:
CPOL=0:空闲状态时,SCK为低电平
CPHA=0:SCK第一个边沿移入数据,第二个边沿移出数据

在W25Q64里面,0x06表示的是写使能。下图所示,由上至下依次为SS、SCK、MOSI、MISO,红色竖线用于间隔时序单元,绿色竖线用于标记读取数据的时刻。

在这里插入图片描述
在空闲状态时,SS为高电平,SCK为低电平,MOSI和MISO的默认电平没有严格规定。

首先,SS产生下降沿,时序开始。 在这个下降沿时刻MOSI和MISO就要开始变换数据了。由于MOSI指令码最高位依然是0,所以这里保持低电平不变。MISO,从机现在没有数据发给主机,引脚电平没有变化(实际上W25Q64不需要回传数据时手册里规定的是MISO仍然是高阻态,从机并没有开启输出,这里因为STM32的MISO是上拉输入,所以这里MISO呈现高电平

然后,SCK第一个上升沿,进行数据采样。 从机采样输入得到0,主机采样输入得到1。接着,SCK第一个下降沿,进行数据输出。 主机输出0,从机输出1。再接着,SCK第二个上升沿,进行数据采样,然后SCK第二个下降沿,进行数据输出 … 如此循环8次,在SCK第八个上升沿时完成一个字节数据交换。

最后,在SCK下降沿之后SS置回高电平,结束通信。

本次通信的结果就是,主机用0x06换来了从机的0xFF。当然实际上从机并没有输出,这个0xFF是默认的高电平,不过这个0xFF没有意义,我们可以不管它,这就是发送单字节指令的时序了。

5.2 指定地址写

这个时序的功能是向SS指定的设备,发送写指令(0x02),随后在指定地址(Address[23:0])下,写入指定数据(Data)

注意:这里的地址是24位3个字节的

在这里插入图片描述

指定地址写的时序跟上面我们讲的发送指令其实道理是差不多的。这些时序都是由一个个交换字节的时序单元组成的,不同的只是比如说上面发送指令之后就完事了,而这里是发送完指令之后要连续发送三个字节的地址指定写的位置,然后再发送一个写入的一个字节数据就行了,最后如果不想继续写就直接将SS置回高电平结束通信即可。

注意:SPI里也会有跟I2C一样的地址指针,每读写一个字节,地址指针自动加1。如果发送一个字节之后不终止,继续发送的字节就会依次写入到后续的存储空间里,这样就可以实现从指定地址开始写入多个字节了。

在这里插入图片描述
最终这条时序实现的功能就是在指定地址0x123456下写入数据0x55。

5.3 指定地址读

向SS指定的设备,发送读指令(0x03),随后在指定地址(Address[23:0])下,读取从机数据(Data)

在这里插入图片描述

同样的套路,起始之后主机发送的第一个字节0x33表示要读取数据,之后还是一样,主机依次交换三个字节地址,分别是0x12、0x34、0x56,组合到一起就是0x123456,代表24位地址。

紧接着,关键点来了,因为我们是要读取数据,指定地址之后显然我们就要开始接收数据了,我们需要随便发送一个数据进行交换(当然也不是随便发的,我们一般会发0XFF),然后从机就会把0x123456地址下的一个字节数据交换过来。如下所示,我们用0xFF跟从机交换了0x55,如果我们想要连续读取多个字节也是一样的道理,这里的指针每读取一次就会自动加1,这里我就不再累述了。

在这里插入图片描述
最后,如果主机不想继续读取数据了就可以把SS置回高电平,结束本次通信。这条时序最终的结果是,主机读取到从机0x123456地址下的数据为0x55。

相关文章:

stm32之SPI通信协议

文章目录 前言一、SPI通信协议1.1 SPI简介1.2 SPI通信特点1.3 SPI与I2C对比 二、SPI硬件电路三、SPI通信原理四、SPI时序单元4.1 起始和终止条件4.2 交换一个字节(模式1)4.3 交换一个字节(模式0)4.4 交换一个字节(模式2和3) 五、SPI时序5.1 发送指令5.2 指定地址写5.3 指定地址…...

Unity 摄像机(Camera)详解

文章目录 0.前言1.相机属性介绍2.Unity 中多个相机画面堆叠显示2.1 3D 摄像机2.2 UI 摄像机2.3 摄像机的Culling Mask设置 0.前言 本文介绍的是使用Unity默认的内置渲染管线下的Camera组件,使用URP或HDRP则不同。 1.相机属性介绍 Clear Flags: 清除标记…...

数学基础 -- 线性代数之LU分解

LU分解 LU分解(LU Decomposition)是线性代数中非常重要的一种矩阵分解方法。它将一个方阵分解为一个下三角矩阵(L矩阵)和一个上三角矩阵(U矩阵)的乘积。在数值线性代数中,LU分解广泛用于求解线…...

高职人工智能训练师边缘计算实训室解决方案

一、引言 随着物联网(IoT)、大数据、人工智能(AI)等技术的飞速发展,计算需求日益复杂和多样化。传统的云计算模式虽在一定程度上满足了这些需求,但在处理海量数据、保障实时性与安全性、提升计算效率等方面…...

【Java】SpringCloud中使用set方法报错空指针

前言:今天在交流群中看见了一个空指针报错,想着哪里为空点过去看看为什么赋不上值就行,没想到啪啪打脸了,今天总结一下。 以下是他的RedisTempate注入和方法 可以看到,89行报错空指针。先分析一下, ①赋值…...

芯片杂谈 -- 常聊的内核包含哪些模块

目录 1. R52内核速览 2. 处理器模块详解 3.内核的功能安全测什么? 4.小结 最开始接触到汽车MCU大都来自NXP、Infineon、Renesas,例如MPC5748、TC275、RH850 P1X等等; 而各大OEM、供应商等等发布的JD通常都会要求熟悉AURIX、PowerPC、G3K…...

运维问题0002:SAP多模块问题-SAP系统程序在执行时,跳出“加急快件”窗口,提示:快件文档“更新已终止”从作者***收到

1、问题描述 近期收到2起业务报障,均反馈在SAP执行程序时,弹出“加急快件”窗口,导致操作的业务实际没有更新完成。 1)业务场景一:设备管理部门在操作事务代码:AS02进行资产信息变更时,保存正常…...

深度解析RAG:你必须要了解的RAG优化方法

RAG(Retrieval-Augmented Generation)是一种结合检索和生成能力的技术框架,旨在通过从外部知识库中检索相关信息来增强生成模型的输出。其基本思想是利用大型语言模型(LLM)的生成能力,同时通过检索机制获取…...

深度学习驱动下的字符识别:挑战与创新

一、引言 1.1 研究背景 深度学习在字符识别领域具有至关重要的地位。随着信息技术的飞速发展,对字符识别的准确性和效率要求越来越高。字符识别作为计算机视觉领域的一个重要研究方向,其主要目的是将各种形式的字符转换成计算机可识别的文本信息。近年…...

使用 JAXB 将内嵌的JAVA对象转换为 xml文件

使用 JAXB 将内嵌的JAVA对象转换为 xml文件 1. 需求2. 实现(1)FileDesc类(2)MetaFileXml类(3)生成对应的xml文件 1. 需求 获取一个目录下所有文件的元数据信息(文件名、大小、后缀等&#xff0…...

若依项目后台启动报错: [网关异常处理]、503

拉取代码启动项目,网关控制台报错: 21:31:59.981 [boundedElastic-7] WARN o.s.c.l.c.RoundRobinLoadBalancer - [getInstanceResponse,98] - No servers available for service: ruoyi-system 21:31:59.981 [boundedElastic-7] ERROR c.r.g.h.Gateway…...

【C++ Qt day10】

2、 完善对话框,点击登录对话框,如果账号和密码匹配,则弹出信息对话框,给出提示”登录成功“,提供一个Ok按钮,用户点击Ok后,关闭登录界面,跳转到其他界面 如果账号和密码不匹配&am…...

GO HTTP库使用

Go的 net/http 包是一个强大且易于使用的库,用于构建HTTP服务器和客户端。通过它,你可以轻松实现HTTP请求的处理、路由、静态文件服务等功能。下面重点以及一个简单的Demo示例。 文章目录 1. **基础HTTP服务器**2. **处理请求与响应**3. **路由与处理器*…...

数据结构 - 顺序表

0.线性表 1.定义 线性表就是零个或多个相同数据元素的有限序列。 2.线性表的存储结构 ①.顺序结构 ②.链式结构 3.线性表的表示方法 例如: 一.线性表的基本运算 二.线性表的复杂运算 1.线性表的合并运算 2.线性表的去重运算 三.顺序表 1.定义 顺序表,就…...

企业如何组建安全稳定的跨国通信网络?

组建一个安全稳定的跨国通信网络对于现代企业来说至关重要,尤其是当企业在全球范围内运营时。以下是一些关键步骤和考虑因素: 需求分析: 确定企业的具体通信需求,包括带宽要求、延迟敏感度、数据类型(如语音、视频、文…...

OCR在线识别网站现已上线!

注意,本文只提供学习的思路,严禁违反法律以及破坏信息系统等行为,本文只提供思路 如有侵犯,请联系作者下架 由作者亲自开发的ocr识别网站哈哈,暂时汇聚了三十多种验证码模型以及算法,欢迎各路朋友去尝试,网站地址如下 http://gbj5w3.natappfree.cc/ocr 验证码类型包括但…...

排名再升2位 中国平安位列BrandZ最具价值中国品牌第9位

9月10日,凯度华通明略发布“2024年BrandZ最具价值中国品牌”榜单,中国平安位列榜单第9位,较2023年榜单排名上升2位,品牌价值韧性增长至205.14亿美元,十度蝉联中国保险行业品牌价值第一位。榜单特别提到,中国…...

k8s集群部署:环境准备

本教程基于centos9 arm架构展开。 1. 设置主机名 为每个节点设置主机别名,以便于集群中的角色识别: # 设置主节点的主机名为 kmaster sudo hostnamectl set-hostname kmaster --static# 设置工作节点1的主机名为 kworker1 sudo hostnamectl set-hostn…...

<C++> set、map模拟实现

目录 一、适配器红黑树 二、红黑树再设计 1. 重新设计 RBTree 的模板参数 2. 仿函数模板参数 3. 正向迭代器 构造 operator*() operator->() operator!() operator() operator--() 正向迭代器代码 4. 反向迭代器 构造 operator* operator-> operator operator-- operat…...

软考学习 数据结构 查找

1. 顺序查找(Sequential Search) 基本原理: 顺序查找是一种最简单、最直观的查找算法。它从数据集合的第一个元素开始,依次与目标元素进行比较,直到找到目标元素或遍历完所有元素为止。 适用条件: 适用…...

零门槛NAS搭建:WinNAS如何让普通电脑秒变私有云?

一、核心优势:专为Windows用户设计的极简NAS WinNAS由深圳耘想存储科技开发,是一款收费低廉但功能全面的Windows NAS工具,主打“无学习成本部署” 。与其他NAS软件相比,其优势在于: 无需硬件改造:将任意W…...

使用VSCode开发Django指南

使用VSCode开发Django指南 一、概述 Django 是一个高级 Python 框架,专为快速、安全和可扩展的 Web 开发而设计。Django 包含对 URL 路由、页面模板和数据处理的丰富支持。 本文将创建一个简单的 Django 应用,其中包含三个使用通用基本模板的页面。在此…...

逻辑回归:给不确定性划界的分类大师

想象你是一名医生。面对患者的检查报告(肿瘤大小、血液指标),你需要做出一个**决定性判断**:恶性还是良性?这种“非黑即白”的抉择,正是**逻辑回归(Logistic Regression)** 的战场&a…...

Vue3 + Element Plus + TypeScript中el-transfer穿梭框组件使用详解及示例

使用详解 Element Plus 的 el-transfer 组件是一个强大的穿梭框组件,常用于在两个集合之间进行数据转移,如权限分配、数据选择等场景。下面我将详细介绍其用法并提供一个完整示例。 核心特性与用法 基本属性 v-model:绑定右侧列表的值&…...

2.Vue编写一个app

1.src中重要的组成 1.1main.ts // 引入createApp用于创建应用 import { createApp } from "vue"; // 引用App根组件 import App from ./App.vue;createApp(App).mount(#app)1.2 App.vue 其中要写三种标签 <template> <!--html--> </template>…...

ABAP设计模式之---“简单设计原则(Simple Design)”

“Simple Design”&#xff08;简单设计&#xff09;是软件开发中的一个重要理念&#xff0c;倡导以最简单的方式实现软件功能&#xff0c;以确保代码清晰易懂、易维护&#xff0c;并在项目需求变化时能够快速适应。 其核心目标是避免复杂和过度设计&#xff0c;遵循“让事情保…...

华硕a豆14 Air香氛版,美学与科技的馨香融合

在快节奏的现代生活中&#xff0c;我们渴望一个能激发创想、愉悦感官的工作与生活伙伴&#xff0c;它不仅是冰冷的科技工具&#xff0c;更能触动我们内心深处的细腻情感。正是在这样的期许下&#xff0c;华硕a豆14 Air香氛版翩然而至&#xff0c;它以一种前所未有的方式&#x…...

管理学院权限管理系统开发总结

文章目录 &#x1f393; 管理学院权限管理系统开发总结 - 现代化Web应用实践之路&#x1f4dd; 项目概述&#x1f3d7;️ 技术架构设计后端技术栈前端技术栈 &#x1f4a1; 核心功能特性1. 用户管理模块2. 权限管理系统3. 统计报表功能4. 用户体验优化 &#x1f5c4;️ 数据库设…...

【7色560页】职场可视化逻辑图高级数据分析PPT模版

7种色调职场工作汇报PPT&#xff0c;橙蓝、黑红、红蓝、蓝橙灰、浅蓝、浅绿、深蓝七种色调模版 【7色560页】职场可视化逻辑图高级数据分析PPT模版&#xff1a;职场可视化逻辑图分析PPT模版https://pan.quark.cn/s/78aeabbd92d1...

VM虚拟机网络配置(ubuntu24桥接模式):配置静态IP

编辑-虚拟网络编辑器-更改设置 选择桥接模式&#xff0c;然后找到相应的网卡&#xff08;可以查看自己本机的网络连接&#xff09; windows连接的网络点击查看属性 编辑虚拟机设置更改网络配置&#xff0c;选择刚才配置的桥接模式 静态ip设置&#xff1a; 我用的ubuntu24桌…...