多线程——04
本节目标
1. wait 和 notify 方法
2. 代码案例
1. wait 和 notify 方法
1. 方法使用
多个线程的执行顺序本身是随机的(抢占式执行)
wait —— 让指定线程进入阻塞状态
notify —— 唤醒对应的阻塞状态的线程
注意: wait, notify, notifyAll 都是 Object 类的方法
wait 在执行的时候要做好三件事:
1)释放当前的锁(释放锁的前提是先加上锁)
2)让线程进入阻塞
3)当线程被唤醒的时候,重新获得到锁
a. wait 和 notify 都是Object方法(死等状态)
wait 等的状态什么都不做,不会占用CPU
b. 调用 wait 不一定只有一个线程调用,N个线程都可以调用。当多个线程调用时,这些线程都会进入阻塞状态,可以用 notifyAll 一次全部唤醒
c. wait 可以是设置一个超时时间——避免wait无休止的等待
wait(时间);
超过设置时间后,线程开始继续执行
2.使用区别
其实理论上 wait 和 sleep 完全是没有可比性的,因为一个是用于线程之间的通信的,一个是让线程阻 塞一段时间,唯一的相同点就是都可以让线程放弃执行一段时间
1. wait 需要搭配 synchronized 使用. sleep 不需要
2. wait 是 Object 的方法 sleep 是 Thread 的静态方法
2. 代码案例
1)单例模式
a. 饿汉模式
在有些场景下,希望有的类型只有一个对象,不能由多个
// 结果为 true(同一个实例)
由SE语法可知:通过static关键字,可以使在类被加载的时候,就会执行到创建实例的方法
1)在类的内部,提供一个现成的实例对象
2)把构造方法设置为私有(private),避免其他代码能够创建出实例对象
b. 懒汉模式
实例的创建时机:
饿汉模式:类加载的时候
懒汉模式:第一次使用的时候(首次调用类的时候才创建)
如果多个线程,同时修改多个变量,可能会出现线程安全问题
如果多个线程,同时读取一个变量,不会出现线程安全问题
此时的懒汉模式,既会读取,也会修改,就可能存在问题!——线程不安全
饿汉模式的 getInstance 只是进行读取 ——线程安全
如何让懒汉模式实现线程安全:
1)new操作不是原子性的(指令重排序)
new操作可以分为三步:
1. 申请指令空间
2. 在内存空间上构造对象(构造方法)
3. 把内存地址赋值给instance引用
在单线程的情况下,new操作的执行顺序无所谓;但在多线程情况下可能会有问题
a. 假设线程 t1 按照1,3,2的执行顺序,执行完1,3时,此时instance已经是非空了,但是此时的instance指向的是一个还没初始化的非法对象
b. 此时 t2 线程开始执行,t2 线程判定instance == null 条件不成立,直接 return instance,此时 t2 线程就有可能访问 instance 里面的属性和方法
因此要对new操作进行加锁
synchronized (SingletonLazy.class){//判断是否new对象if(instance == null){instance = new SingletonLazy();} }由于每次加锁和释放锁的的过程非常消耗CPU,降低了运行效率,所以再加一层If语句,判断 instance 是否已经非空,为空再进入程序
由于 new 操作会触发指令重排序,所以使用 volatile 关键字
正确代码如下:
单例模式还有以下问题:
1. 使用反射,能否打破单例
2. 使用序列化/反序列化,能否打破单例
2)阻塞队列
多线程代码中比较常用到的数据结构,是一种特殊的队列:
1. 线程安全
2. 带有阻塞特性
1)如果队列为空,继续出队列,就会阻塞,直到其他线程往队列里添加元素为止
2)如果队列为满,继续入队列,就会阻塞,直到其他线程往队列里取走元素为止
java标准库里,已经提供了现成的阻塞队列,可以直接使用
标准库里,针对Blocking Queue提供了两种这个主要的实现方式:
1. 基于数组
2. 基于链表
Queue提供的方法在阻塞队列的模拟实现中不建议使用,以为都不具备“阻塞”特性:
put —— 阻塞特性的入队列
take —— 阻塞特性的出队列
BlockingQueue 是一个接口 真正实现的类是 LinkedBlockingQueue
put 方法用于阻塞式的入队列, take 用于阻塞式的出队列
BlockingQueue 也有 offer, poll, peek 等方法, 但是这些方法不带有阻塞特性
程序仍在运行
现在来回顾一些循环队列的实现:
类属性的定义
类方法的实现
阻塞队列的实现:
一个队列要么空,要么满——take和put只有一边阻塞
如果take阻塞,其他线程调用take也会阻塞,只有靠put中的notify才能唤醒;put阻塞同样
在当前代码中如果interrupt唤醒wait,整个方法直接就结束了(throws)
如果是try/throw出现异常,代码不会结束,会继续往下执行(导致错误)
关键要点:当wait返回时,要进一步判断当前队列是否是满/空的
——>期望wait返回后再执行一次判断条件,条件成立,继续wait
使用wait时,可以使用while作为条件判定的方式——>让wait唤醒后,再确认一下条件是否满足
(java官方文档给出的建议)
阻塞队列还可以用来实现 “生产者—消费者模型”
3)定时器
约定一个时间,时间到达后,执行某个代码逻辑。定时器非常常见的日常开发组件,尤其是进行网络通信的时候
java标准库中也提供了定时器的实现:
定义一个timer添加多个任务(runnable),每个任务同时都会带有一个时间(delay)
1. Timer内置了线程(前台线程),需手动停止,否则timer不知道是否还要添加任务
——> timer.cancle();
2. 不能使用 lambda 表达式
得有函数式接口,interface 里面只能有这一个方法
3. 此处使用匿名内部类,继承 TimeTask 并且创建出一个实例,目的是为了重写run,通过run描述任务的详细情况
TimeTask 实现了 Runnable 接口
4. delay 决定当前任务什么时候执行,填写的时间以当前时刻为基准,再往后推
此刻传入的时间是“绝对时间”(完整的时间戳) // “相对时间”(时间间隔)
计时器的模拟实现:
1)创建一个类MyTimeTask,通过类对象来描述一个任务(至少包括任务内容和时间)
定义任务和时间,并重写构造方法(决定 time ——执行时间)
由于当前类是自定义的,实现比较要重写 compareTo 方法,并提供任务和时间的获取方法
2)需要一个数据结构,把所有任务都保存起来
创建一个优先级队列里保存任务,并创建一个方法实现任务的“入队列”
优先级队列并非是线程安全的,所以要加锁
3)定义一个类Timer,Timer中需要一个线程,扫描任务是否到时间可以执行了
1)创建一个线程不断扫描(while循环)当前的队首元素,看是否到达执行时间
2)在while循环内,先判断队列是否为空,若为空则 wait 阻塞等待直到入队列操作唤醒
3)若不为空,则 peek 出队首元素与当前时间比较一下,判断是否执行
4)若达到执行时间,则执行程序 t.starrt();
5)如未达到执行时间,使用待时间的 wait (时间为预计时间的差值,避免重复执行while循环,消耗CPU资源)
1)注意以上有两个 wait 需要唤醒——>PriorityBlockingQueue(阻塞队列)不方便实现这样的两处等待
2)为了唤醒第一处的 wait (队列为空),可以在入队列操作时加入 notify 唤醒
3)第一处的队列为空判断while,是为了防止 interrupt 唤醒 wait(try/catch 抛出异常后,程序仍然继续运行)
4)最后一处的 wait 是否可以使用 sleep ? ——>不可以
当入队列一个执行时间更小的任务时,可以使用 schedule 唤醒这里的 wait ,让while再走一遍,重新拿到队首元素
4)线程池
1. 定义
使用多线程进行并发编程,需要频繁的创建销毁进程,成本较大
引入线程(轻量级进程)复用资源,来提高创建销毁的效率
随着销毁创建线程的频率进一步提升,开销依然无法忽略不计:
1)协程/纤程(轻量级线程)
2)线程池
提前把要是用的线程在线程池中准备好,需要用时就从池子里取,用完之后就还给池子
——>纯用户态代码,比内核操作更快,更可控
1)从线程池取——>纯用户态
创建新线程——>用户态+内核态
2)如果一段程序是在操作系统内核中执行——>内核态
3)操作系统是由 内核+配套的应用程序 构成,内核是操作系统最核心的部分
创建线程的操作需要调用系统API,进入到内核中,按照内核态的方式完成一系列的动作
4)操作系统内核是要给所有的进程提供服务的,当创建线程时,可能会做一些其他的事情,是不可控的
纯用户态是可控的
2. 标准库中的使用
标准库中,ThreadPoolExecutor 类表示线程池
ThreadPoolExecutor的参数:
1)int corePoolSize,int maximumPoolSize
核心线程数 最大线程数
2)long keepAliveTime,TimeUnit unit
保持存活时间 时间单位(s,min,ms,hour)
线程的空闲时间超过时间阈值(keepAliveTime),就会被销毁
3)BlockingQeque<Runnable> workQueue
和定时器类似,线程池中可以持有很多任务,也可以使用PriorityBlockingQueue(优先级)
使用 Runnable 来作为描述任务的主体
4)ThreadFactory threadFactory 线程工厂
工厂模式(设计模式),通过专门的“工厂类”/“工厂对象”来创建指定对象
通过这个工厂类,创建线程对象(Thread)
在这个类里面提供了方法(不一定是静态的),让方法封装 new Thread 操作,同时给Thread设置一些属性,构成了 ThreadFactory 线程工厂
在C++/Java中要想提供多个版本的构造方法,就需要让这多个构造方法能构成重载
重载要求:
1. 方法名相同 2. 形参的个数/类型不同
把工厂方法放到一个其他的类中,这个类就叫做“”工厂类
通过静态方法封装new操作,在放方法内部设定不同的属性完成对像的初始化,构造对象
——>工厂模式
5)RejectedExecutionHandler handler 拒绝策略
1. ThreadPoolExecutor.AbortPolicy —— 继续执行任务,直接抛出异常
新旧任务都不执行
2. ThreadPoolExecutor.CallerRunsPolicy —— 新的任务由添加任务的线程执行
新任务会由调用者执行,不是线程池
3. ThreadPoolExecutor.DiscardOldestPolicy —— 丢弃最老的任务
4. ThreadPoolExecutor.DiscardPolicy —— 丢弃最新的任务
新的任务不执行(调用的线程,线程池都不会执行)
3. Executors
ThreadPoolExecutor 本身使用较为复杂,因此标准库中还提供了另一个版本,把 ThreadPoolExecutor封装了一下
Executors 工厂类 通过这个类创建出不同的线程池对象(在内部把 ThreadPoolExecutor 创建好并且设置了不同的参数)
1) Executors.newFixedThreadPool();
线程数目固定
2)Executors.newCachedThreadPool();
线程数目能动态扩容
3)Executors.newSingleThreadExecutor();
只包含单个线程的线程池
4)Executors.newSingleThreadExecutor();
定时器类似物,能延时执行任务
Executors //简单调用
ThreadPoolExecutor //高度定制化
创建线程的时候,线程池的线程数量设置为多少合适?
1)如果一个进程中,所有的线程都是CPU密集型,每个线程所有的工作都是在CPU上执行,此时线程的数目不应该超过N(CPU逻辑核心数)
2)如果一个进程中,所有的线程都是IO密集型,每个线程所有的工作都是在等待IO,此时线程的数目可以远远超过超过N
尝试给线程池设定不同的线程数目,分别进行能测试,衡量每种线程数目下,总的时间开销和系统资源占用的开销,找到两者之间的合适值
CPU密集型—— 这个线程大部分时间都要在CPU上运行,进行计算
IO密集型—— 这个线程大部分时间否在等待IO,不需要去CPU上执行
4. 线程池的模拟实现
1)提供构造方法,指定创建多少个线程
2)在构造方法中,把这些线程都创建好
3)有一个阻塞队列,能够持有要执行的任务
4)提供 submit 方法,可以添加新任务
方法的调用:
可以发现当前代码报错了——>
lanbda 表达式的“变量获取”只能获取 final 值(Java中没有全局变量的概念)
在 submit 内部定义一个 n (事实final)变量
每次循环,都会有一个新的 n ,n 本身没有改变,就可以被捕获
程序不会停止,等待新的任务添加执行
多线程之间的执行顺序是不确定的,某个线程渠道某个任务,但是并非立即执行,这个过程另一个线程就插到前面了
上述的这些线程,彼此之间都是等价的
相关文章:
多线程——04
本节目标 1. wait 和 notify 方法 2. 代码案例 1. wait 和 notify 方法 1. 方法使用 多个线程的执行顺序本身是随机的(抢占式执行) wait —— 让指定线程进入阻塞状态 notify —— 唤醒对应的阻塞状态的线程 注意: wait, notify, notifyAl…...
使用ECS和OSS搭建个人网盘
在linux服务器 一、下载cloudreve安装包。 执行如下命令,下载cloudreve安装包。 wget https://labfileapp.oss-cn-hangzhou.aliyuncs.com/cloudreve_3.3.1_linux_amd64.tar.gz 下载完毕后,执行如下命令,解压cloudreve安装包。 tar -zxvf c…...
Android 单元测试断言校验方法 org.junit.Assert
判断布尔值 assertTrue assertFalse 判断对象非空 assertNull(object); 案例: PersistableBundle result Util.getCarrierConfig(mockContext, subId);assertNull(result); 判断是否相等 assertEquals("mocked_string", result.toString()); package or…...
SpringSecurity学习
介绍 SpringSecurity是一个作用于身份认证和权限控制的框架,其针对的主要就是网站的安全问题 页面代码 要使用SpringSecurity的前提是有一个可以正常访问业务逻辑的代码,再使用SpringSecurity实现权限控制和身份验证。 后端代码 package com.learn.…...
Eureka和Zookeeper、Nacos的区别
目录 一、Eureka与Zookeeper的区别 适用场景: 架构设计: 功能特性: 社区生态: 二、Eureka与Nacos的区别 接口方式: 实例类型: 健康检测: 服务发现: 一致性与可用性&#…...
基于gitlab API刷新MR的commit的指定status
场景介绍 自己部署的gitlab Jenkins,并已经设置好联动(如何设置可以在网上很容易搜到)每个MergeRequest都可以触发多个Jenkins pipeline,pipeline结束后会将状态更新到gitlab这个MR上希望可以跳过pipeline运行,直接将指定的MR的指定pipeline状态刷新为…...
SpringBoot | 拦截器 | 统一数据返回格式 | 统一异常处理 | 适配器模式
拦截器 拦截器是Spring框架提供的核心功能之一, 主要用来拦截用户的请求, 在指定方法前后, 根据业务需要执行预先设定的代码. 也就是说, 允许开发人员提前预定义一些逻辑, 在用户的请求响应前后执行. 也可以在用户请求前阻止其执行. 在拦截器当中,开发人员可以在…...
Oracle清除水位
– 清除水位 ALTER TABLE 数据库名.表名 ENABLE ROW MOVEMENT; ALTER TABLE 数据库名.表名 SHRINK SPACE CASCADE; ALTER TABLE 数据库名.表名 DISABLE ROW MOVEMENT; – 回收统计信息 BEGIN DBMS_STATS.GATHER_TABLE_STATS(OWNNAME > ‘数据库名’, TABNAME > ‘表名’…...
软件工程——期末复习(2)
Part1:软件工程基本概念 软件程序文档数据 在软件工程中,软件通常被定为程序、文档和数据的集合。程序是按事先设计的功能和性能要求编写的指令序列;程序是完成指定功能的一段特定语言代码。文档是描述程序操作和使用的文档,是与…...
RAID1技术是什么?它的发展和工作原理如何?
RIAD1是一种先进的数据存储与冗余技术,设计用于解决现代分布式系统中常见的数据安全、数据一致性和高可用性等问题。随着云计算和大规模分布式存储系统的兴起,如何保障数据在高效传输与存储过程中仍然能具备足够的安全性和可靠性,成为了各大企…...
【Apache Paimon】-- 8 -- flink 创建 paimon connecor 的两种方式
目录 1、使用 catalog 创建非临时表 2、使用 with 创建 temporary 表 3、对比 4、参考 1、使用 catalog 创建非临时表 CREATE CATALOG my_catalog WITH (type = paimon,warehouse = hdfs:///path/to/warehouse );USE CATALOG my_catalog; CREATE TABLE `<your-paimon-…...
js进阶-关于运算符++
一、运算符与表达式 运算符按参与的运算单元数量分为:一元运算符、二元运算符和三元运算符;表达式是运算单元和运算符一起构成的;每个表达式都有一个运算后的返回值。 二、关于运算符 1.概述 运算符分为两部分,第一部分是返回运…...
三维地图,智慧城市,商业智能BI,数据可视化大屏(Cesiumjs/UE)
绘图工具 三维地图:Cesiumjs 建模方式:激光点云建模、航拍倾斜摄影建模、GIS建模、BIM建模、手工建模 建模工具:C4D Blender GeoBuilding ArcGIS Cesiumjs <!DOCTYPE html> <html lang"en"> <head><meta …...
通过EPEL 仓库,在 CentOS 7 上安装 OpenResty
通过EPEL 仓库,在 CentOS 7 上安装 OpenResty 通过EPEL 仓库,在 CentOS 7 上安装 OpenResty步骤 1: 安装 EPEL 仓库步骤 2: 安装 OpenResty步骤 3: 启动 OpenResty步骤 4: 设置开机自启步骤 5: 验证安装说明 通过EPEL 仓库,在 CentOS 7 上安装…...
每日一题 LCR 054. 把二叉搜索树转换为累加树
LCR 054. 把二叉搜索树转换为累加树 使用后序遍历即可 class Solution { public:TreeNode* convertBST(TreeNode* root) {int temp 0;dfs(root,temp);return root;}void dfs(TreeNode* root,int &temp){if(!root){return ;}dfs(root->right,temp);temp root->val;…...
【贪心算法】贪心算法五
贪心算法五 1.跳跃游戏 II2.跳跃游戏3.加油站3.单调递增的数字 点赞👍👍收藏🌟🌟关注💖💖 你的支持是对我最大的鼓励,我们一起努力吧!😃😃 1.跳跃游戏 II 题目链接&…...
vue2播放视频和预览文件的组件以及使用方法
##文件预览组件 按照组件 解决展示pdf的问题 npm install pdfh5 npm install canvas2.8.0 --ignore-scripts npm install --save dommatrix npm install --save web-streams-polyfill解决excel和docx预览的问题 npm install vue-office/docx vue-demi0.14.6 npm inst…...
记录一下,解决js内存溢出npm ERR! code ELIFECYCLEnpm ERR! errno 134 以及 errno 9009
项目是个老项目,依赖包也比较大,咱就按正常流程走一遍来详细解决这个问题,先看一下node版本,我用的是nvm管理的,详细可以看我的其他文章 友情提醒:如果项目比较老,包又大,又有一些需…...
【批处理脚本】更改Windows系统中的 hosts 解析文件
概述 作用 修改 Windows 系统中的 hosts 文件,可以实现 插入 或 删除 条目。该脚本允许用户以管理员权限执行,将特定的域名解析到指定的 IP 地址 应用场景 非常适用于需要频繁或批量修改 hosts 文件的场景: 屏蔽网站、域名重定向、DNS 污染防…...
AIGC 与艺术创作:变革与机遇
在当今数字化时代,人工智能生成内容(AIGC)正以惊人的速度重塑着艺术创作的格局,为艺术家们带来了令人振奋的新机遇。 一.AIGC 的崛起与艺术领域的变革 随着人工智能技术的不断进步,AIGC 逐渐在艺术领域崭露头角。它依…...
String IP和Int IP的互相转换
android中,wifiManager.connectionInfo.ipAddress 可以获取到wifi的ip地址,但这是一个int值,如何转换为常见的如192.168.1.129这种形式,以及这种形式如何转换回int值的形式。 这里ip分为4段,每一段的值都是0 ~ 255&am…...
【大数据学习 | 面经】yarn的资源申请和分配的单位-Container
在yarn中,资源的申请和分配是以container为单位进行的,而不是直接以application和task为单位。 每个提交到yarn上的应用程序(application)都有一个对应的ApplicationMaster(AM)。这个AM负责与ResourceMana…...
php基础:文件处理2
1.文件属性 当我们在程序中操作文件时,可能会使用到文件的一些常见属性,比如文件的大小、类型、修改时间、访问时间以及权限等等。PHP 中提供了非常全面的用来获取这些属性的内置函数,如下表所示。 2.目录操作 新建目录:mkdir(路…...
gradle下载慢解决方案2024 /12 /1android studio (Windows环境)
gradle下载慢解决方案2024 /12 /1 默认环境配置好了,环境配置和程序安装请出门右转 打开软件,点击右上角设置,找到如下设置页 选择本地安装并制定好你已经安装好的 gradle 应用保存即可 全局插件环境配置(新版本可以直接在设置中添加了) 找对应位置添加国内源并把前面的内置源…...
使用Java将PDF文件解析成Excel文件
安装pom依赖 <!-- 解析pdf--><dependency><groupId>org.apache.pdfbox</groupId><artifactId>pdfbox</artifactId><version>2.0.27</version> <!-- 请检查并使用最新版本 --></dependency>测试读取pdf文件…...
怎么区分直线模组中的导程和行程?
直线模组是一种直线传动装置,安装方便,精度高,其使用范围广。直线模组中的导程和行程是两个不同的概念,它们分别描述了直线模组的不同性能参数。 直线模组的行程指的是模组能够正常移动的最大距离,即滑块预期移动的有效…...
算法日记 42 day 图论
今天来看看广度优先搜索,并且写几个题。刷到这里我才想起来,当时第一次面试的时候问的就是这个题,当时大概知道一点思路,但不清楚是图论方面的,更别说写出来了。 广度优先搜索(BFS) 不同于深度…...
STM32 GPIO 8种工作模式的应用场景
目录 一、四种输入模式1、模拟输入:2、浮空输入:3、上拉输入:4、下拉输入: 二、四种输出模式1、推挽输出:2、开漏输出:3、复用推挽输出:4、复用开漏输出: 一、四种输入模式 1、模拟…...
JVM 类加载器有哪些?双亲委派机制的作用是什么?如何自定义类加载器?
类加载器分类 大家好,我是码哥,可以叫我靓仔,《Redis 高手心法》畅销书作者。 先回顾下,在 Java 中,类的初始化分为几个阶段: 加载、链接(包括验证、准备和解析)和 初始化。 而 类加载器&#x…...
揭秘:短视频矩阵源码功能开发分析!!!
一、短视频矩阵系统源码概述 短视频矩阵系统源码旨在为内容创作者及企业提供一种高效的工具,以实现对多个短视频账户的一站式管理。该系统支持同时管理、发布、监控和优化多达1000个短视频账户,显著提升了操作效率。 二、主要功能 1. 多账号管理 该系…...
leetcode - 2337. Move Pieces to Obtain a String
Description You are given two strings start and target, both of length n. Each string consists only of the characters ‘L’, ‘R’, and ‘_’ where: The characters ‘L’ and ‘R’ represent pieces, where a piece ‘L’ can move to the left only if there i…...
第九篇:k8s 通过helm发布应用
什么是helm? Helm 是 Kubernetes 的包管理器。Helm 是查找、分享和使用软件构建 Kubernetes 的最优方式。 在红帽系的Linux中我们使用yum来管理RPM包,类似的,在K8s中我们可以使用helm来管理资源对象(Deployment、Service、Ingress…...
MySQL:锁机制
锁是计算机协调多个进程或线程并发访问某一资源的机制(避免争抢)。 在数据库中,除传统的计算资源(如 CPU、RAM、I/O 等)的争用以外,数据也是一种供许多用户共享的资源。如何保证数据并发访问的一致性、有效…...
在lio_sam中融入GPS
文章目录 概要GPS里程计GPS因子反算后的GPS里程计概要 在LIO(激光惯性里程计)系统中,将GPS信息融合到里程计中,借助GTSAM(Georgia Tech Smoothing and Mapping)库进行因子图优化,可以有效提升全局定位精度。 GPS里程计 利用GeographicLib第三方库将经纬度投影到局部笛…...
快速构建NLP理论知识体系
NLP理论知识体系 一句话解释NLPNLP模型及原理简述1、Rag 一句话解释NLP 如果我们要实现机器翻译、情感分析、问答系统、文本摘要、聊天机器人、构造智能化的辅助文件填写模板,NLP可以通过现成的模型对输入的语音、文字、图片进行处理(分词、标词性、去停…...
长期稳定境外号码解决方案:内地用户如何打电话、接收短信和验证码
文章目录 📖 介绍 📖🏡 演示环境 🏡📒 三大方案对比 📒📝 免费且稳定的境外号码📝 长期稳定且符合本地政策📝 适合低频使用者⚓️ 相关链接 ⚓️📖 介绍 📖 许多用户在日常生活中需要拨打境外电话、接收短信或验证码,尤其是跨境电商从业者,更是对境外号…...
SpringCloud 与 SpringBoot版本对应关系,以及maven,jdk
目录 SpringCloud 与 SpringBoot各版本的对应关系 方式一 Learn 方式二 OverView SpringBoot与JDK、maven 容器等对应关系 SpringCloud 与 SpringBoot各版本的对应关系 SpringCloudSpringBootFinchley2.0.xFinchley.SR1Spring Boot >=2.0.3.RELEASE and <=2.0.9RELEAS…...
FSMC实验
FSMC ,即灵活的静态存储控制器,能够与同步或异步存储器和 16 位 PC 存储器卡连接, STM32 的 FSMC 接口支持包括 SRAM 、 NAND FLASH 、 NOR FLASH 和 PSRAM 等存储器。 从上图我们可以看出, STM32 的 FSMC 将外部设…...
K8s命令大全(Complete List of K8s Commands)
💝💝💝欢迎来到我的博客,很高兴能够在这里和您见面!希望您在这里可以感受到一份轻松愉快的氛围,不仅可以获得有趣的内容和知识,也可以畅所欲言、分享您的想法和见解。 本人主要分享计算机核心技…...
C++学习笔记
小甲鱼学习课程 02 #include <iostream> 头文件 iostream iostream 翻译为IO流 输入输出流 using namespace std; 引入命名空间 c标准库所使用的所有标识符都是在同一个特殊的名字空间std中来定义的; 偷懒使用这句话; std::cout <…...
伺服控制电机多大功率合适?
随着现代工业自动化的发展,伺服控制电机在各个行业的应用愈加广泛。伺服电机以其精确的控制、高效的运行和高响应速度,成为许多机械设备中不可或缺的组成部分。然而,在选择伺服电机时,确定其功率大小是一个关键环节。那么…...
《OpenCV 基础全攻略:从入门到精通》
《OpenCV 基础全攻略:从入门到精通》 一、OpenCV 简介(一)特点(二)优势(三)应用场景 二、安装与配置三、OpenCV 函数详解1. 图像读取函数 cv2.imread ()2. 图像显示函数 cv2.imshow ()3. 图像保…...
spring ai如何使用function call调用第三方模型
这里写自定义目录标题 背景什么是function call怎么用function call?总结 背景 一直困惑于ai是如何使用插件或者其他一些功能的,后来发现,很多大模型都支持function call功能,如何让大模型能够联网查询呢,function ca…...
2024 数学建模国一经验分享
2024 数学建模国一经验分享 背景:武汉某211,专业:计算机科学 心血来潮,就从学习和组队两个方面指点下后来者,帮新人避坑吧 2024年我在数学建模比赛中获得了国一(教练说论文的分数是湖北省B组第一࿰…...
javaweb-Mybaits
1.Mybaits入门 (1)介绍 (2) 2.Mybaits VS JDBC 3.数据库连接池 (1)SpringBoot默认连接池为hikari,切换为Druid有两种方式 方式一:加依赖 方式二:直接修改配置文件 …...
108.【C语言】数据结构之二叉树查找值为x的节点
目录 1.题目 代码模板 2.分析 分类讨论各种情况 大概的框架 关键部分(继续递归)的详解 递归调用展开图 3.测试结果 其他写法 4.结论 5.注意事项 不推荐的写法 1.题目 查找值为x的节点并返回节点的地址 代码模板 typedef int BTDataType; typedef struct BinaryT…...
Ant-Design-Vue 全屏下拉日期框无法显示,能显示后小屏又位置错乱
问题1:在全屏后 日期选择器的下拉框无法显示。 解决:在Ant-Design-Vue的文档中,很多含下拉框的组件都有一个属性 getPopupContainer可以用来指定弹出层的挂载节点。 在该组件上加上 getPopupContainer 属性,给挂载到最外层盒子上。 <temp…...
sec啥意思
sec的基本含义是秒,是时间的基本单位之一;在数学中表示正割函数;在计算机科学中有时指安全;在法语中意为干的等。 sec的多重含义与应用 sec在数学中的定义 在数学领域,尤其是三角学中,sec代表正割函数&a…...
云计算vspere 安装过程
1 材料的准备 1 安装虚拟机 vmware workstation 2 安装esxi 主机 3 在esxi 主机上安装windows 2018 dns 服务器 4 在虚拟机上安装windows 2018 服务器 6 安装vcenter 5 登入界面测试 这里讲一下,由于部署vspere 需要在windows 2012 服务器上部…...
spring-boot打包前重新拉取maven依赖
在使用 Maven 构建 Spring Boot 项目时,如果希望在每次打包时都强制拉取依赖,可以通过以下方法实现。 方法一:在命令行强制更新依赖 在执行 mvn package 或 mvn install 等命令时,添加 -U 参数: mvn clean package -…...