STM32新建不同工程的方式
新建工程的方式
- 1. 安装开发工具 MDK5 / keil5
- 2. CMSIS 标准
- 3. 新建工程
- 3.1 寄存器版工程
- 3.2 标准库版工程
- 3.3 HAL/LL库版工程
- 3.4 HAL库、LL库、标准库和寄存器对比
- 3.5 库开发和寄存器的关系
- 4. STM32CubeMX工具的作用
1. 安装开发工具 MDK5 / keil5
MDK5
由两个部分组成:MDK Core 和 Software Packs。其中,Software Packs 可以独立于工具链进行新芯片支持和中间库的升级。
- MDK Core 分为四个部分:
uVision IDE with Editor(编辑器)
,ARM C/C++ Compiler(编译器)
,Pack Installer(包安装器)
,uVision Debugger with Trace(调试跟踪器)
。Pack Installer 用于下载、安装、更新和管理 Software Packs。- Software Packs(软件包) 分为三个部分:
Device(芯片支持)
,CMSIS(微控制器软件接口标准)
,Mdidleware(中间库)
。
特性 MDK5 Keil5 定位 完整的开发套件 集成开发环境(IDE) 包含内容 IDE、编译器、调试器、中间件、设备支持包 仅包含 IDE 适用场景 ARM Cortex-M 微控制器开发 嵌入式开发(尤其是 ARM Cortex-M) 功能范围 更广泛,包含完整的开发工具链 专注于代码编辑、编译和调试 适用项目规模 开发复杂的嵌入式系统,或者需要使用丰富的中间件 只需要一个 IDE 来编写和调试代码,或者项目规模较小
2. CMSIS 标准
因为基于 Cortex 系列芯片采用的内核都是相同的,区别主要为核外的片上外设的差异,这些差异却导致软件在同内核,不同外设的芯片上移植困难。为了解决不同的芯片厂商生产的 Cortex 微控制器软件的兼容性问题,ARM 与芯片厂商建立了
CMSIS 标准
(微控制器软件接口标准)。所有芯片厂家的官方库
(包括ST官方库)都是根据这套标准设计的。
从图中可以看出,CMSIS 层在整个系统中是处于中间层,向下负责与内核和各个外设直接打交道,向上提供实时操作系统用户程序调用的函数接口。如果没有 CMSIS 标准,那么各个芯片公司就会设计自己喜欢的风格的库函数,而 CMSIS 标准就是要强制规定,芯片生产公司设计的库函数必须按照 CMSIS 这套规范来设计。
其实不用讲这么复杂的,举一个简单的例子,我们在使用 STM32 芯片的时候首先要进行系统初始化,CMSIS 规范就规定,系统初始化函数名字必须为 SystemInit,所以各个芯片公司写自己的库函数的时候就必须用 SystemInit 对系统进行初始化。CMSIS 还对各个外设驱动文件的文件名字规范化,以及函数名字规范化等等一系列规定。例如函数
GPIO_ResetBits
这个函数名字也是不能随便定义的,是要遵循 CMSIS 规范的。
CMSIS 分为 3 个基本功能层:
- 核内外设访问层:用于访问内核寄存器的名称、地址定义以及功能函数,
ARM 公司提供
。- 中间件访问层:用于访问中间件的通用 API,
ARM 公司提供
。- 外设访问层:提供片上的核外外设的地址和中断定义以及外设的访问函数,
芯片生产商提供
。
3. 新建工程
3.1 寄存器版工程
必备文件 描述 位置 stm32f4xx.h 标准外设库头文件,包含寄存器定义、外设地址映射、位域定义等内容。ST官方提供 STM32Cube_FW_F4_V1.26.0\Drivers\
CMSIS\Device\ST\STM32F4xx\Include
startup_stm32f407xx.s 汇编语言启动文件,主要进行初始化堆栈,定义中断向量表以及跳转到主程序main()。ST官方提供 STM32Cube_FW_F4_V1.26.0\Drivers\
CMSIS\Device\ST\STM32F4xx\Source\
Templates\arm
3.2 标准库版工程
标准外设库 是对 STM32 芯片的一个完整的封装,包括所有标准器件外设的器件驱动器,是 ST 最早推出的针对 STM 系列主控的库函数。标准外设库仍然接近于寄存器操作,主要就是将一些基本的寄存器操作封装成了 C 函数。开发者仍需要关注所使用的外设是在哪个总线之上,具体寄存器的配置等底层信息。
ST 为各系列提供的标准外设库稍微有些区别。例如,STM32F1x 的库和 STM32F4x 的库在文件结构上就有些不同,此外,在内部的实现上也稍微有些区别,这个在具体使用(移植)时,需要注意一下!但是,不同系列之间的差别并不是很大,而且在设计上是相同的。
STM32 的标准外设库涵盖以下 3 个抽象级别:
- 包含位,位域和寄存器在内的完整的
寄存器地址映射
- 涵盖所有外围功能(具有公共 API 的驱动器)的例程和数据结构的集合。
- 一组包含所有可用外设的示例,其中包含最常用的开发工具的模板项目。
上图黄色部分为新建工程所必须的内容,接下来介绍这些文件的作用
文件名 作用 类别 是否必须 stm32f4xx_conf.h 1.
用户配置文件,启用或禁用外设驱动: 通过条件编译控制是否包含特定外设的头文件用户层 是 stm32f4xx_it.c
stm32f4xx_it.h1.
用户定义和处理与内核
及外设
相关的中断事件,不一定放到这个文件,可删除用户层 否 stm32f4xx.h 1.
定义所有外设寄存器及其位于 (寄存器定义)
2.
使用结构体组织相关寄存器 (外设结构体)
3.
定义外设寄存器的基地址和偏移量 (地址映射)
4.
定义中断向量号和中断处理 (中断定义)
5.
定义一些常用宏,用于位操作、寄存器配置等 (常用宏)
6.
定义标准数据类型,如uinit32_t
(类型定义)
7.
包含外设的配置选项和默认设置 (外设配置)CMSIS
核心层是 system_stm32f4xx.c
system_stm32f4xx.h1.
实现SystemInit()
函数,负责在系统启动时初始化关键硬件模块 (系统初始化)
2.
实现SystemCoreClockUpdate()
函数,用于更新全局变量SystemCoreClock
的值 (系统时钟更新)
3.
定义全局变量SystemCoreClock
,用于存储系统核心时钟频率 (全局变量定义)
4.
定义默认的时钟配置,确保系统以正确的频率运行 (默认时钟配置)
5.
在启动文件中,SystemInit()
函数会在 main() 函数执行之前被调用,确保系统在进入用户代码之前完成初始化 (与启动文件配合)CMSIS
核心层是 startup_stm32f40xx.s 1.
定义中断向量表
2.
初始化堆栈指针
3.
在复位后初始化 .data 和 .bss 段
4.
调用系统初始化函数SystemInit()
5.
跳转到用户的主程序main()
6.
提供默认的中断处理函数CMSIS
核心层是 core_cm4.h 1.
定义内核的寄存器结构体和地址映射,包括NVIC、SCB、SysTick、MPU、FPU
(定义内核寄存器)
2.
提供一系列内联函数,用于方便地访问内核的功能 (提供内联函数)
3.
定义特殊功能寄存器(如xPSR、CONTROL、PRIMASK 等
),用于控制处理器的运行状态 (定义特殊功能寄存器)
4.
定义FPU
相关的寄存器和函数,用于配置和控制 FPU (支持 FPU)
5.
提供 CMSIS 标准接口
6.
与标准外设库stm32f4xx.h
配合使用,提供对内核功能的访问 (与标准外设库配合)CMSIS
核心层是 core_cmFunc.h 1.
提供内联函数访问内核的特殊功能寄存器(如xPSR、CONTROL、PRIMASK 等
)
2.
支持特权和非特权模式的切换
3.
提供中断控制函数(如全局中断的使能和禁用)
4.
支持浮点单元(FPU)操作(如果可用)CMSIS
核心层是 core_cmInstr.h 1.
定义内联函数,用于封装内核的汇编指令(如WFI、WFE、SEV、NOP 等
)
2.
提供同步指令(如ISB、DSB、DMB
)
3.
支持低功耗模式指令(如WFI 和 WFE
)CMSIS
核心层是 core_cmSimd.h 1.
定义 SIMD 指令的访问函数
2.
提供对 DSP 扩展指令的支持CMSIS
核心层是 stm32f4xx_ppp.c
stm32f4xx_ppp.h1.
提供操作外设的 API 函数
2.
定义外设的寄存器结构体、函数声明和宏定义设备
驱动层是
标准外设库各文件间的关系:
3.3 HAL/LL库版工程
LL 库
(Low Layer)目前与 HAL 库捆绑发布,它设计为比 HAL 库更接近于硬件底层的操作,代码更轻量级,代码执行效率更高的库函数组件,可以完全独立于 HAL 库来使用,但 LL库不匹配复杂的外设,如 USB 等。所以 LL 库并不是每个外设都有对应的完整驱动配置程序。使用 LL 库需要对芯片的功能有一定的认知和了解,它可以:
- 独立使用,该库完全独立实现,可以完全抛开 HAL 库,只用 LL 库编程完成。
- 混合使用,和 HAL 库结合使用。
HAL 库和 LL 库设计为彼此独立的分支,但又同属于 HAL 库体系。标准库和 HAL 库、LL 库完全相互独立,HAL 库更倾向于外设通用化,扩展组件中解决芯片差异操作部分;LL倾向于最简单的寄存器操作,ST 在未来还将重点维护和建设 HAL 库,标准库已经部分停止更新。HAL 库和 LL 库的应用将是未来的一个趋势。
HAL
即硬件抽象层。HAL 库是 ST 公司提供的外设驱动代码的驱动库,用户只需要调用库的 API 函数,便可间接配置寄存器。我们要写程序控制 STM32 芯片,其实最终就是控制它的寄存器,使之工作在我们需要得模式下,HAL 库将大部分寄存器的操作封装成了函数,我们只需要学习和掌握 HAL 库函数的结构和用法,就能方便地驱动 STM32 工作,以节省开发时间。HAL 库开发,指的是利用 HAL 库里面封装好的 C 语言编写的驱动文件,来实现对 STM32 内部和外部电器元件的控制过程。但只有 HAL 库还不能直接驱动一个 STM32 的芯片,其他的组件已经由 ARM 与众多芯片硬件、软件厂商指定的通用的软件开发标准 CMSIS 实现了。
STM32Cube 是 ST 提供的一套性能强大的免费开发工具和嵌入式软件模块,它包含两个关键部分:
- 允许用户通过图形配置工具
STM32CubeMX
来生成 C 语言工程。可以通过 STM32CubeMX 实现方便地下载各种软件或开发固件包。- 嵌入式软件包
(STM32Cube 库)
包含完整的 HAL 库(硬件抽象层 API),配套的中间件(包括 RTOS、USB、FAT文件系统、图形、TCP/IP 、以太网),以及一系列完整的例程。
上图黄色部分为新建工程所必须的内容,接下来介绍这些文件的作用
文件名 作用 类别 是否
必须stm32f4xx_it.c
stm32f4xx_it.h同 标准外设库
一样用户层 否 stm32f4xx_hal_conf.h 同 标准外设库
中 stm32f4xx_conf.h 作用一样用户层 是 stm32f4xx_hal_msp.c 回调函数存放文件,已删除 用户层 否 stm32f407xx.h 同 标准外设库
中 stm32f4xx.h 作用一样CMSIS
核心层是 system_stm32f4xx.c
system_stm32f4xx.h同 标准外设库
一样CMSIS
核心层是 startup_stm32f407xx.s 同 标准外设库
一样CMSIS
核心层是 stm32f4xx.h 是所有 STM32F4 系列的顶层头文件,并且可以选择性包含某一特定的
STM32F4 系列芯片的头文件(比如包含:F407头文件 stm32f407xx.h)CMSIS
核心层是 core_cm4.h 同 标准外设库
一样CMSIS
核心层是 cmsis_armcc.h
cmsis_armclang.h
cmsis_compiler.h
cmsis_version.h
mpu_armv7.h内核头文件,一般都不需要去了解 CMSIS
核心层是 sm32f4xx_hal.c
stm32f4xx_hal.hHAL 库的初始化、系统滴答,HAL 库延时函数等功能 设备
驱动层是 stm32f4xx_hal_def.h 通用 HAL 库资源定义 设备
驱动层是 stm32f4xx_hal_ppp.c
stm32f4xx_hal_ppp.h外设的操作 API 函数文件 设备
驱动层是 stm32f4xx_hal_ppp_ex.c
stm32f4xx_hal_ppp_ex.h拓展外设特性的 API 函数文件 设备
驱动层是 stm32f4xx_II_ppp.c
stm32f4xx_II_ppp.hLL 库文件
,在一些复杂外设中实现底层功能设备
驱动层是
HAL库各文件间的关系:
3.4 HAL库、LL库、标准库和寄存器对比
HAL库 标准库 LL库 寄存器 使用频率 最高 逐渐减少 逐渐增加 较低 优点 开发效率高 代码简洁,代码效率较高 代码效率高,高于标准库 代码效率最高 缺点 代码体积大,执行效率低 已停止维护 开发效率略低于HAL库 开发难度大,可移植性差 使用场景 快速开发、跨平台移植 老项目、简单应用 性能与开发效率平衡的场景 高性能需求、底层开发 开发效率 最高 较高 中等 最低 代码性能 较低 中等 较高 最高
3.5 库开发和寄存器的关系
寄存器(Register)是单片机内部一种特殊的内存,它可以实现对单片机各个功能的控制,简单的来说可以把寄存器当成一些控制开关,控制包括内核及外设的各种状态。所以无论是 51单片机还是 STM32,都需要用寄存器来实现各种控制,以完成不同的功能。
由于寄存器资源非常宝贵,一般都是一个位或者几个位控制一个功能,对于 STM32 来说,其寄存器是 32 位的,一个 32 位的寄存器,可能会有 32 个控制功能,相当于 32 个开关,由于STM32 的复杂性,它内部有几百个寄存器,所以整体来说 STM32 的寄存器还是比较复杂的。不过,我们不要被其吓到了,实际上 STM32 是由于内部有很多外设,所以导致寄存器很多,实际上我们把它分好类,每个外设也就那么几个或者几十个寄存器,学起来就不难了。
从大方向来区分,STM32 寄存器分为两类,如表所示:
其中,内核寄存器,我们一般只需要关心中断控制寄存器和 SysTick 寄存器即可,其他三大类,我们一般很少直接接触。
对于STM32 来说,以 GPIOB 的 ODR 寄存器为例,其寄存器地址为:0X40010C0C,我们对其赋值 0XFFFF,表示 GPIOB 所有 IO 口(16 个 IO 口)都输出高电平:(*(unsigned int *))(0X40010C0C) = 0XFFFF;
虽然上面的代码实现了我们需要的功能,但是从实用的角度来说,这么写肯定是不好的,可读性极差,可维护性也很差,所以一般我们使用结构体来访问,比如改写成这样:
GPIOB->ODR = 0XFFFF;
这种方法当然可以,但是这种方法的劣势是你需要去掌握每个寄存器的用法,你才能正确使用STM32,而对于 STM32 这种级别的 MCU,数百个寄存器记起来又是谈何容易。于是 ST(意法半导体)推出了官方固件库,固件库将这些寄存器底层操作都封装起来,提供一整套接口(API)供开发者调用,大多数场合下,你不需要去知道操作的是哪个寄存器,你只需要知道调用哪些函数即可。
比如控制 BSRRL 寄存器实现电平控制,官方 HAL 库封装了一个函数:void HAL_GPIO_WritePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin, GPIO_PinState PinState) {assert_param(IS_GPIO_PIN(GPIO_Pin));assert_param(IS_GPIO_PIN_ACTION(PinState));if(PinState != GPIO_PIN_RESET){GPIOx->BSRR = GPIO_Pin;}else{GPIOx->BSRR = (uint32_t)GPIO_Pin << 16;} }
这个时候你不需要再直接去操作BSRRL寄存器了,你只需要知道怎么使用HAL_GPIO_WritePin这个函数就可以了。在你对外设的工作原理有一定的了解之后,你再去看固件库函数,基本上函数名字能告诉你这个函数的功能是什么,该怎么使用,这样开发起来会方便很多。
任何处理器,不管它有多么的高级,归根结底都是要对处理器的寄存器进行操作。但是固件库不是万能的,如果想要把 STM32 学透,光读 STM32 固件库是远远不够的。你还是要了解一下 STM32 的原理,了解 STM32 各个外设的运行机制。只有了解了这些原理,你在进行固件库开发过程中才可能得心应手游刃有余。只有了解了原理,才能做到“知其然知其所以然”,所以在学习库函数的同时,别忘了要了解一下寄存器大致配置过程。
标准库
函数是对寄存器简单的进行了一次封装
。将每个功能都独立的封装成一个函数。每个函数的功能比较单一。而HAL库
相当于对寄存器进行了二次或者三次的封装
,它将能合并的功能都合并在了一起。减小了写代码的难度。但是库函数本身阅读起来要比标准库要费劲一些。这样就导致,如果程序出错的话调试起来要比标准库难一点。但是HAL写程序却比较简单,函数的名字也更容易理解。更接近于面向对象的思想。没有哪种方式更好,每种都有自己的优缺点,根据实际情况,自己喜欢用哪种就用那种。通过对官方的这两种库的对比,可以看出在产品开发中代码永远都有优化和改进的空间。以后自己在开发项目的时候,也可以用这两种不同的方式对自己的代码进行优化升级。
描述 标准外设库 HAL / LL库 内核寄存器 封装文件
core_cm4.h core_cm4.h 内核寄存器 操作文件
1.
core_cm4.h
2.
misc.c / misc.h : 封装NVIC、SysTick等
操作
3.
system_stm32f4xx.c : 系统初始化和时钟配置函数,涉及对内核寄存器的操作
4.
startup_stm32f40xx.s: 底层汇编代码,涉及内核寄存器初始化1.
core_cm4.h
2.
stm32f4xx_hal_cortex.c : 封装对内核寄存器的操作
3.
system_stm32f4xx.c : 系统初始化和时钟配置函数,涉及对内核寄存器的操作
4.
startup_stm32f40xx.s: 底层汇编代码,涉及内核寄存器初始化
5.
stm32f4xx_hal.c: 间接操作内核寄存器外设寄存器 封装文件
stm32f4xx.h stm32f4xx.h 外设寄存器 操作文件
stm32f4xx_ppp.c
stm32f4xx_ppp.hstm32f4xx_hal_ppp.c
stm32f4xx_hal_ppp.h
stm32f4xx_hal_ppp_ex.c
stm32f4xx_hal_ppp_ex.h
stm32f4xx_II_ppp.c
stm32f4xx_II_ppp.h
4. STM32CubeMX工具的作用
STM32CubeMX是一款图形化配置工具,主要用于STM32微控制器的初始化和代码生成。 其主要作用包括:
引脚配置:
可视化配置引脚功能,如GPIO、外设接口等,避免冲突。时钟树配置:
通过图形界面配置系统时钟、外设时钟等,确保时钟设置正确。外设配置:
配置外设参数,如UART、SPI、I2C、ADC等,生成初始化代码。中间件配置:
配置FreeRTOS、FATFS、USB库等中间件,简化开发。功耗配置:
配置低功耗模式,优化功耗管理。代码生成:
生成初始化代码,支持多种IDE(如Keil、IAR、STM32CubeIDE等),并提供HAL库和LL库选项。项目管理:
创建和管理项目,支持多种开发环境和工具链。固件更新:
集成STM32固件更新功能,方便升级。
通过STM32CubeMX工具自动生成驱动代码,让开发者只需专注实现 应用逻辑。
相关文章:
STM32新建不同工程的方式
新建工程的方式 1. 安装开发工具 MDK5 / keil52. CMSIS 标准3. 新建工程3.1 寄存器版工程3.2 标准库版工程3.3 HAL/LL库版工程3.4 HAL库、LL库、标准库和寄存器对比3.5 库开发和寄存器的关系 4. STM32CubeMX工具的作用 1. 安装开发工具 MDK5 / keil5 MDK5 由两个部分组成&#…...
Java数据库操作指南:快速上手JDBC【学术会议-2025年数字化教育与信息技术(DEIT 2025】
大会官网:www.ic-deit.org 前言 在现代企业应用中,数据库是数据存储和管理的重要组成部分。Java作为一种广泛使用的编程语言,提供了多种方式与数据库进行交互。本文将介绍 JDBC(Java Database Connectivity)&#x…...
基于Springboot + vue实现的在线装修管理系统
“前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默,忍不住分享一下给大家。点击跳转到网站:人工智能学习网站” 💖学习知识需费心, 📕整理归纳更费神。 🎉源码免费人人喜…...
计算机网络之应用层
本文章目录结构出自于《王道计算机考研 计算机网络_哔哩哔哩_bilibili》 05 应用层 在网上看到其他人做了相关笔记,就不再多余写了,直接参考着学习吧。 王道考研 计算机网络笔记 第六章:应用层_王道考研 应用层 笔记-CSDN博客 DNS&#x…...
SpringMVC框架
第1章 SpringMVC入门 1.1 SpringMVC简介 Spring MVC 全称:Spring Web MVC是 Spring 框架的一部分,专注于实现 Web 应用程序的模型-视图-控制器(Model-View-Controller, MVC)设计模式。它为构建灵活且松耦合的 Web 应用提供了强大的功能&…...
将 OneLake 数据索引到 Elasticsearch - 第 1 部分
作者:来自 Elastic Gustavo Llermaly 学习配置 OneLake,使用 Python 消费数据并在 Elasticsearch 中索引文档,然后运行语义搜索。 OneLake 是一款工具,可让你连接到不同的 Microsoft 数据源,例如 Power BI、Data Activ…...
flutter跨端UI框架简介
flutter跨端UI框架简介 简介 Flutter是由Google开发的开源应用开发框架,主要用于构建高性能、跨平台的移动、Web和桌面应用程序。Flutter使用Dart语言,提供了一套丰富的Widgets,使开发者能够快速创建美观的用户界面。其最大特点是热重载功能…...
Centos 修改历史读录( HISTSIZE)
history命令 -c #清空命令历史 -r #读历史文件附加到历史列表 -w #保存历史列表到指定的历史文件 命令历史相关环境变量 HISTSIZE #命令历史记录的条数 HISTFILE #指定历史文件,默认为~/.bash_history HISTFILESIZE #命令历史文件记录历史的条数 以上变量可以 exp…...
利用ML.NET精准提取人名
在当今信息爆炸的时代,文本处理任务层出不穷,其中人名提取作为基础且重要的工作,广泛应用于信息检索、社交网络分析、客户关系管理等领域。随着人工智能不断进步,ML.NET作为微软推出的开源机器学习框架,为开发者提供了…...
关于deepin上运行Qt开发的程序
国产化替代是将来各单位的主流趋势,探索自行开发应用程序在国产操作系统上正常运行是将来的主要工作之一。本文浅尝gui程序在统信社区版——deepin上遇到的小问题。 使用Qt在deepin上做了一个类似gif的帧动画弹窗,在编译运行时,程序可以正常…...
3.3 Go函数可变参数
可变参数(variadic parameters)是一种允许函数接受任意数量参数的机制。它在函数定义中使用 ...type 来声明参数类型,所有传递的参数会被收集为一个切片,函数内部可以像操作普通切片一样处理这些参数。 package mainimport "…...
Queries Acceleration -Tuning- Tuning Execution 学习笔记
1 Adjustment of RuntimeFilter Wait Time 1.1 Case: Too Short RuntimeFilter Wait Time 1.1.1 没有看懂,好像是等待时间过小也会导致性能下降 1.1.2 set runtime_filter_wait_time_ms = 3000; 2 Data Skew Handling 2.1 Case 1: Bucket Data Skew Leading to Suboptimal …...
VS C++ 配置OPENCV环境
VS C 配置OPENCV环境 1.下载opencv2.安装环境3.opencv环境4.VS配置opencv环境5.EXE执行文件路径的环境lib和dll需要根据是debug还是release环境来区分使用哪个 6.Windows环境 1.下载opencv 链接: link 2.安装环境 双击运行即可 3.opencv环境 include文件路径:opencv\build\…...
Midscene.js:重新定义UI自动化的新时代工具
前言 Midscene.js 是一个创新的、面向开发者的 UI 自动化解决方案,并通过人工智能技术简化自动化脚本的编写与维护。 它提供了三种核心方法——交互(.ai, .aiAction)、提取(.aiQuery)和断言(.aiAssert&am…...
记录让cursor帮我给ruoyi-vue后台管理项目整合mybatis-plus
自己整合过程中会出现 work.web.exception.GlobalExceptionHandler :100 | 请求地址/admin/device/install/detail/1,发生未知异常. org.apache.ibatis.binding.BindingException: Invalid bound statement (not found): com.fire.mapper.DeviceInstallMapper.selectById at o…...
uniapp中h5的微应用解决办法
考虑过用wujie,参考官网Vue组件封装 | 无界的教程,虽然没报错,但是子应用的vue节点根本没挂载上,不知道什么原因,如下图所示 后面采用iframe方式将子应用导入进来: 父应用: <template>&…...
再尝Semantic Kernel,planning特性很香
背景 书接上回《浅尝semantic kernel》; 上次只试了试SK框架的插件特性,这次试了下编排的特性,也就是把多个本地任务按顺序按逻辑执行,没想到效果也是出奇的好! 关键步骤 架构层面的代码本篇不在赘述,这…...
华为OD机试真题---战场索敌
华为OD机试真题“战场索敌”是一道考察算法和数据结构应用能力的题目。以下是对该题目的详细解析: 一、题目描述 有一个大小是NM的战场地图,被墙壁’#‘分隔成大小不同的区域。上下左右四个方向相邻的空地’.‘属于同一个区域,只有空地上可…...
Case逢无意难休——深度解析JAVA中case穿透问题
Case逢无意难休——深度解析JAVA中case穿透问题~ 不作溢美之词,不作浮夸文章,此文与功名进取毫不相关也!与大家共勉!! 更多文章:个人主页 系列文章:JAVA专栏 欢迎各位大佬来访哦~互三必回&#…...
HTML入门知识
目录 一、什么是HTML 二、HTML文档的语法规则 三、HTML基本标签 四、HTML注释与特殊字符 1、注释 2、特殊字符 五、HTML属性 六、常见误区与建议 一、什么是HTML HTML,全称Hyper Text Markup Language,即超文本标记语言,是一种用于创…...
idea maven本地有jar包,但还要从远程下载
idea 中,java 工程执行 maven reimport,报jar报无法下载。 我奇了个怪,我明明在本地仓库有啊,你非得从远程下载? 我从供应商那里拿来的,远程当然没有了。 这太奇葩了吧,折腾好久不行。 后来…...
利用大语言模型(LLM)增强软件测试自动化的最佳实践
在当今迅速变化的科技时代,软件测试行业面临着越来越高的效率和质量要求。作为测试专家,我们都知道,传统的测试方法往往无法满足快速迭代和高效交付的需求。在这种背景下,自动化测试逐渐成为解决方案的一部分。而大语言模型&#…...
联想电脑怎么设置u盘启动_联想电脑设置u盘启动方法(支持新旧机型)
有很多网友问联想电脑怎么设置u盘启动,联想电脑设置u盘启动的方法有两种,一是通过bios进行设置。二是通过快捷方式启动进入u盘启动。但需要注意有两种引导模式是,一种是uefi引导,一种是传统的leacy引导,所以需要注意制…...
Browser-Use WebUI项目启动指南
摘要 此前发布《Browser - Use WebUI 使用体验》博文后,鉴于部分朋友运行时出现问题,重新运行并整理相关内容。本文详细记录 Web UI 项目启动全过程,涵盖 Python 3.11、Chrome 浏览器及 API Keys 等环境要求,Python 环境检查、依赖…...
期权帮|如何利用股指期货进行对冲套利?
锦鲤三三每日分享期权知识,帮助期权新手及时有效地掌握即市趋势与新资讯! 如何利用股指期货进行对冲套利? 对冲就是通过股指期货来平衡投资组合的风险。它分为正向与反向两种策略: (1)正向对冲ÿ…...
基于springboot的酒店客房管理系统----数据库课程设计
目录 1.需求分析 1.1用例模型 1.1.1用例图 1.1.2用例描述 1.2过程模型 1.2.1数据流 1.2.2数据字典 1.3 安全性和完整性需求 1.4?数据字典 1.4.1数据项 1.4.2数据结构 1.4.3数据流 1.4.4数据存储 1.4.5数据过程 2概念结构设计 2.1 ER模型 2.1.1 实体及属性 2…...
SPDK vhost介绍
目录 1. vhost技术的背景与动机Virtio 介绍virtio-blk数据路径为例 2. vhost技术的核心原理2.1 vhost-kernel2.2 vhost-user举例 2.3 SPDK vhostvhost的优势IO请求处理数据传输控制链路调整 3. SPDK vhost的实现与配置3.1 环境准备3.2 启动SPDK vhost服务3.3 创建虚拟块设备3.4…...
理解C++运行时类型识别符: typeid
1. 格式 typeid (type-id) typeid (expression) typeid 运算符允许在运行时确定对象的类型。 typeid 的结果是一个 const type_info&。该值是对 type_info 对象的引用,该对象表示 type-id 或表达式的类型,具体取决于使用哪种形式的 typeid。有关…...
Fullcalendar @fullcalendar/react 样式错乱丢失问题和导致页面卡顿崩溃问题
问题描述: 我使用 fullcalendar的react版本时,出现了一个诡异的问题,当我切换到 一个iframe页面时(整个页面是一个iframe嵌入的),再切换回来日历的样式丢失了!不仅丢失了样式还导致页面崩溃了&…...
C++从入门到实战(二)C++命名空间
C从入门到实战(二)C命名空间 前言一、C的第一个程序二、命名空间(一)为什么需要命名空间(二)定义命名空间(三)使用命名空间1.通过命名空间限定符:2.使用 using 声明&…...
Spring 定时任务:@Scheduled 注解四大参数解析
本文主要介绍了在 Spring 框架中使用Scheduled注解实现定时任务的方法,重点讲解了fixedRate、fixedDelay、cron和initialDelay这四个参数的用法,并通过实例代码进行了详细说明。 1. fixedRate 参数 参数含义 fixedRate指定任务固定时间间隔执行。如设…...
计算机网络之物理层
本文章目录结构出自于《王道计算机考研 计算机网络_哔哩哔哩_bilibili》 01 物理层 在网上看到其他人做了详细的笔记,就不再多余写了,直接参考着学习吧。 1 详解物理层-通信基础【王道计算机网络笔记】_wx63088f6683f8f的技术博客_51CTO博客 2 详解物…...
Oracle 数据库常见字段类型大全及详细解析
在工作期间会遇到数据库建表的业务,经常会使用复制粘帖等操作,而不清楚数据库的字段类型。本文记录了 Oracle 数据库常见字段类型,根据不同的数据需求,可以选择不同的字段类型来存储数据。 文章目录 一、字符类型(Char…...
总线、UART、IIC、SPI
一图流 总线 概念 连接多个部件的信息传输线,是各部件共享的传输介质 类型 片内总线:连接处理器内核和外设的总线,在芯片内部 片外总线:连接芯片和其他芯片或者模块的总线 总线的通信 总线通信的方式 串行通信 数据按位顺序传…...
纯css实现div宽度可调整
<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8" /><meta name"viewport" content"widthdevice-width, initial-scale1.0" /><title>纯css实现div尺寸可调整</title><style…...
Arduino大师练成手册 -- 读取DHT11
要在 Arduino 上控制 DHT11 温湿度传感器,你可以按照以下步骤进行: 硬件连接: 将 DHT11 的 VCC 引脚连接到 Arduino 的 5V 引脚。 将 DHT11 的 GND 引脚连接到 Arduino 的 GND 引脚。 将 DHT11 的 DATA 引脚连接到 Arduino 的数字引脚&am…...
GS论文阅读--GeoTexDensifier
前言 本文是一个关于高斯致密化策略对高斯地图进行优化,他主要关注了几何结构和纹理信息。我最近对于高斯点的分布比较感兴趣,因为高斯点的分布决定了之后重建质量的好坏,初始化高斯很重要,但之后的维护需要致密化与修建策略&…...
Android实战经验篇-玩转Selinux(详解版)
列文章转如下链接: Android Display Graphics系列文章-汇总 Android实战经验篇-系列文章汇总 本文主要包括部分: 一、Selinux概述 1.1 SELinux是什么? 1.2 自主访问控制(DAC) 1.3 强制访问控制(MAC&…...
【langgraph】ubuntu安装:langgraph:未找到命令
langgraph 在ubuntu24.04 参考:langgraph运行:报错: (05_ep_dev) root@k8s-master-pfsrv:/home/zhangbin/perfwork/01_ai/05_ep_dev/expert# langgraph dev langgraph:未找到命令查看langraph的安装情况 pip show langgraph...
深入探究分布式日志系统 Graylog:架构、部署与优化
文章目录 一、Graylog简介二、Graylog原理架构三、日志系统对比四、Graylog部署传统部署MongoDB部署OS或者ES部署Garylog部署容器化部署 五、配置详情六、优化网络和 REST APIMongoDB 七、升级八、监控九、常见问题及处理 一、Graylog简介 Graylog是一个简单易用、功能较全面的…...
HTML新春烟花
系列文章 序号目录1HTML满屏跳动的爱心(可写字)2HTML五彩缤纷的爱心3HTML满屏漂浮爱心4HTML情人节快乐5HTML蓝色爱心射线6HTML跳动的爱心(简易版)7HTML粒子爱心8HTML蓝色动态爱心9HTML跳动的爱心(双心版)1…...
CentOS 7 安装fail2ban hostdeny方式封禁ip —— 筑梦之路
centos 7 换源参考CentOS 7.9 停止维护(2024-6-30)后可用在线yum源 —— 筑梦之路_centos停止维护-CSDN博客 安装fail2ban yum install fail2ban 新增配置文件 cat > /etc/fail2ban/action.d/hostsdeny.conf << EOF [Definition] actionstart actionstop action…...
java入门基础笔记语法篇(3)
一、 注释 什么是注释 注释定义:注释是写在程序中对代码进行解释说明的文字,方便自己和他人查看以理解程序。 Java注释的三种写法: 单行注释:以“//”开头,注释内容只能写一行。多行注释:以“/*”开头&…...
VUE对接deepseekAPI调用
1.先去开放平台注册账号申请api key。开放平台:https://platform.deepseek.com/api_keys 2.你的项目需要有发送请求的axios或者自己写。 npm install axios # 或 yarn add axios 3.创建 API 调用函数 在 Vue 项目中,通常会将 API 调用的逻辑封装到一个…...
【C++高并发服务器WebServer】-1:Linux中父子进程fork创建及关系、GDB多进程调试
本文目录 一、进程创建二、GDB多进程调试 一、进程创建 在Linux中输入man 2 fork可以查看man文档中的fork的相关函数信息。 fork的作用就是创建一个子进程。 通过fork我们可以知道,创建子进程的时候,复制父进程的信息。 我们看看翻译的man文档信息&am…...
leetcode——相交链表(java)
给你两个单链表的头节点 headA 和 headB ,请你找出并返回两个单链表相交的起始节点。如果两个链表不存在相交节点,返回 null 。 图示两个链表在节点 c1 开始相交: 题目数据 保证 整个链式结构中不存在环。 注意,函数返回结果后&…...
Spring 框架:配置缓存管理器、注解参数与过期时间
在 Spring 框架中,可通过多种方式配置缓存具体行为,常见配置方法如下。 1. 缓存管理器(CacheManager)配置 基于内存的缓存管理器配置(以SimpleCacheManager为例) SimpleCacheManager 是 Spring 提供的简单…...
UDP協議與代理IP介紹
UDP,全稱是用戶數據報協議(User Datagram Protocol),是Internet協議套組的一部分,與TCP協議一道工作。與TCP相比,UDP可以理解為一個更“羽量級”的協議。它不需要像TCP那樣在數據傳輸開始之前建立連接&…...
24.日常算法
1. 数组中两元素的最大乘积 题目来源 给你一个整数数组 nums,请你选择数组的两个不同下标 i 和 j,使 (nums[i]-1)*(nums[j]-1) 取得最大值。请你计算并返回该式的最大值。 示例 1: 输入:nums [3,4,5,2] 输出:12 解释…...
【Python】FastAPI框架快速实现后端(一)
FastAPI框架快速实现后端-SQLModel的使用 介绍正文基础模型模型与表定义数据表模型关系定义 介绍 最近1个多月,用FastAPI做了几个日常工作用的小功能,感觉FastAPI确实很适合这种场景,功能要求简单,交付要求比较急,这个…...