Promise用法详解
文章目录
- 一、异步代码的困境
- 1.异步任务的处理
- 二、认识Promise作用
- 1.什么是Promise呢?
- 2.Promise的代码结构
- 三、Promise状态变化
- 1.Executor
- 2.resolve不同值的区别
- 3.then方法 – 接受两个参数
- 4.then方法 – 多次调用
- 5.then方法 – 返回值
- 6.catch方法 – 多次调用
- 7.catch方法 – 返回值
- 五、Promise实例方法
- 1.finally方法
- 六、Promise的类方法
- 1.resolve方法
- 2.reject方法
- 3.all方法
- 4.allSettled方法
- 5.race方法
- 6.any方法
一、异步代码的困境
1.异步任务的处理
在ES6出来之后,有很多关于Promise的讲解、文章,也有很多经典的书籍讲解Promise
- 虽然等你学会Promise之后,会觉得Promise不过如此;
- 但是在初次接触的时候都会觉得这个东西
不好理解
;
那么这里我从一个实际的例子来作为切入点:
- 我们调用一个函数,这个函数中发送网络请求(我们可以用定时器来模拟);
- 如果发送网络请求成功了,那么告知调用者发送成功,并且将相关数据返回过去;
- 如果发送网络请求失败了,那么告知调用者发送失败,并且告知错误信息;
// 1.设计这样的一个函数
function execCode(counter, successCallback, failureCallback) {// 异步任务setTimeout(() => {if (counter > 0) { // counter可以计算的情况 let total = 0for (let i = 0; i < counter; i++) {total += i}// 在某一个时刻只需要回调传入的函数successCallback(total)} else { // 失败情况, counter有问题failureCallback(`${counter}值有问题`)}}, 3000)
}// 2.ES5之前,处理异步的代码都是这样封装
execCode(100, (value) => {console.log("本次执行成功了:", value)
}, (err) => {console.log("本次执行失败了:", err)
})
二、认识Promise作用
1.什么是Promise呢?
在上面的解决方案中,我们确确实实可以解决请求函数得到结果之后,获取到对应的回调,但是它存在两个主要的问题:
- 第一,我们需要自己来设计
回调函数
、回调函数的名称、回调函数的使用等; - 第二,对于不同的人、不同的框架设计出来的方案是不同的,那么我们必须耐心去看别人的源码或者文档,以便可以理解它
这个函数到底怎么用
;
我们来看一下Promise的API是怎么样的:
- Promise是一个类,可以翻译成 承诺、许诺 、期约;
- 当我们需要的时候,给予调用者一个承诺:待会儿我会给你回调数据时,就可以创建一个Promise的对象;
- 在通过new创建Promise对象时,我们需要传入一个回调函数,我们称之为
executor
- 这个回调函数会被
立即执行
,并且给传入另外两个回调函数resolve
、reject
; - 当我们调用resolve回调函数时,会执行Promise对象的then方法传入的回调函数;
- 当我们调用reject回调函数时,会执行Promise对象的catch方法传入的回调函数;
- 这个回调函数会被
2.Promise的代码结构
我们来看一下Promise代码结构:
function execCode(counter) {const promise = new Promise((resolve, reject) => {// 异步任务setTimeout(() => {if (counter > 0) { // counter可以计算的情况 let total = 0for (let i = 0; i < counter; i++) {total += i}// 成功的回调resolve(total)} else { // 失败情况, counter有问题// 失败的回调reject(`${counter}有问题`)}}, 3000)})return promise
}// const promise = execCode(100)
// promise.then((value) => {
// console.log("成功有了结果: ", value)
// })
// promise.catch((err) => {
// console.log("失败有了错误: ", err)
// })// const promise2 = execCode(-100)
// promise2.then(value => {
// console.log("成功:", value)
// })
// promise2.catch(err => {
// console.log("失败:", err)
// })// 执行一次
execCode(255).then(value => {console.log("成功:", value)
}).catch(err => {console.log("失败:", err)
})
上面Promise使用过程,我们可以将它划分成三个状态:
- 待定(pending): 初始状态,既没有被兑现,也没有被拒绝;
- 当执行executor中的代码时,处于该状态;
- 已兑现(fulfilled): 意味着操作成功完成;
- 执行了resolve时,处于该状态,Promise已经被兑现;
- 已拒绝(rejected): 意味着操作失败;
- 执行了reject时,处于该状态,Promise已经被拒绝;
三、Promise状态变化
1.Executor
Executor是在创建Promise时需要传入的一个回调函数,这个回调函数会被立即执行,并且传入两个参数:
通常我们会在Executor中确定我们的Promise状态:
- 通过resolve,可以兑现(fulfilled)Promise的状态,我们也可以称之为
已决议
(resolved); - 通过reject,可以拒绝(reject)Promise的状态;
这里需要注意:一旦状态被确定下来,Promise的状态会被 锁死,该Promise的状态是不可更改的
- 在我们调用resolve的时候,如果resolve传入的值本身不是一个Promise,那么会将该Promise的状态变成
兑现
(fulfilled); - 在之后我们去调用reject时,已经不会有任何的响应了(并不是这行代码不会执行,而是无法改变Promise状态);
// 1.创建一个Promise对象
const promise = new Promise((resolve, reject) => {// 注意: Promise的状态一旦被确定下来, 就不会再更改, 也不能再执行某一个回调函数来改变状态// 1.待定状态 pendingconsole.log("111111")console.log("222222")console.log("333333")// 2.兑现状态 fulfilledresolve()// 3.拒绝状态 rejectedreject()
})promise.then(value => {console.log("成功的回调")
}).catch(err => {console.log("失败的回调")
})// executor
const promise2 = new Promise((resolve, reject) => {})
2.resolve不同值的区别
情况一:如果resolve传入一个普通的值或者对象
,那么这个值会作为then回调的参数;
情况二:如果resolve中传入的是另外一个Promise
,那么这个新Promise会决定原Promise的状态:
情况三:如果resolve中传入的是一个对象
,并且这个对象有实现then方法
,那么会执行该then方法,并且根据then方法的结果来决定Promise的状态:
const p = new Promise((resolve) => {// setTimeout(resolve, 2000)setTimeout(() => {resolve("p的resolve")}, 2000)
})const promise = new Promise((resolve, reject) => {// 1.普通值// resolve([// {name: "macbook", price: 9998, intro: "有点贵"},// {name: "iPhone", price: 9.9, intro: "有点便宜"},// ])// 2.resolve(promise)// 如果resolve的值本身Promise对象, 那么当前的Promise的状态会有传入的Promise来决定// resolve(p)// 3.resolve(thenable对象)resolve({name: "kobe",then: function(resolve) {resolve(11111)}})
})promise.then(res => {console.log("then中拿到结果:", res)
})
3.then方法 – 接受两个参数
then方法是Promise对象上的一个方法(实例方法):
- 它其实是放在Promise的原型上的 Promise.prototype.then
then方法接受两个参数:
fulfilled
的回调函数:当状态变成fulfilled时会回调的函数;reject
的回调函数:当状态变成reject时会回调的函数;
4.then方法 – 多次调用
一个Promise的then方法是可以被多次调用的:
- 每次调用我们都可以传入对应的
fulfilled
回调; - 当Promise的状态变成fulfilled的时候,这些回调函数都会被执行;
const promise = new Promise((resolve, reject) => {resolve("success")// reject("failure")
})// promise.then(res => {
// }).catch(err => {
// })// 1.then参数的传递方法: 可以传递两个参数
// 这种写法也是可以的
// promise.then(res => {
// console.log("成功回调~", res)
// }, err => {
// console.log("失败回调~", err)
// })promise.then(res => {console.log("成功回调~", res)
})
promise.then(res => {console.log("成功回调~", res)
})
promise.then(res => {console.log("成功回调~", res)
})
promise.then(res => {console.log("成功回调~", res)
})
5.then方法 – 返回值
then方法本身是有返回值的,它的返回值是一个Promise,所以我们可以进行如下的链式调用
:
- 但是then方法返回的Promise到底处于什么样的状态呢?
Promise有三种状态,那么这个Promise处于什么状态呢?
- 当then方法中的
回调函数本身在执行
的时候,那么它处于pending状态; - 当then方法中的
回调函数返回一个结果
时,那么它处于fulfilled状态,并且会将结果作为resolve的参数;- 情况一:返回一个普通的值;
- 情况二:返回一个Promise;
- 情况三:返回一个thenable值;
- 当then方法抛出一个异常时,那么它处于
reject
状态;
const promise = new Promise((resolve, reject) => {resolve("aaaaaaa")// reject()
})// 1.then方法是返回一个新的Promise, 这个新Promise的决议是等到then方法传入的回调函数有返回值时, 进行决议
// Promise本身就是支持链式调用
// then方法是返回一个新的Promise, 链式中的then是在等待这个新的Promise有决议之后执行的
// promise.then(res => {
// console.log("第一个then方法:", res)
// return "bbbbbbbb"
// }).then(res => {
// console.log("第二个then方法:", res)
// return "cccccccc"
// }).then(res => {
// console.log("第三个then方法:", res)
// })// promise.then(res => {
// console.log("添加第二个then方法:", res)
// })// 2.then方法传入回调函数的返回值类型
const newPromise = new Promise((resolve, reject) => {setTimeout(() => {resolve("why")}, 3000)
})promise.then(res => {console.log("第一个Promise的then方法:", res)// 1.普通值// return "bbbbbbb"// 2.新的Promise// return newPromise// 3.thenable的对象return {then: function(resolve) {resolve("thenable")}}
}).then(res => {console.log("第二个Promise的then方法:", res) // undefined
})
6.catch方法 – 多次调用
catch方法也是Promise对象上的一个方法(实例方法):
- 它也是放在Promise的原型上的 Promise.prototype.catch
一个Promise的catch方法是可以被多次调用的:
- 每次调用我们都可以传入对应的reject回调;
- 当Promise的状态变成reject的时候,这些回调函数
都会被执行
;
const promise = new Promise((resolve, reject) => {reject("failure")
})promise.then(res => {console.log("成功的回调:", res)
}).catch(err => {console.log("失败的回调:", err)
})promise.catch(err => {console.log("失败的回调:", err)
})
promise.catch(err => {console.log("失败的回调:", err)
})
promise.catch(err => {console.log("失败的回调:", err)
})
promise.catch(err => {console.log("失败的回调:", err)
})
7.catch方法 – 返回值
事实上catch方法也是会返回一个Promise对象的,所以catch方法后面我们可以继续调用then方法或者catch方法:
- 下面的代码,后续是catch中的err2打印,还是then中的res打印呢?
const promise = new Promise((reslove, reject) => {console.log("promise executor开始执行")reject(111)
})
promise.catch(res => {console.log("err:" + res)
}).catch(res => {console.log("err2:" + res)
}).then(res2 => {console.log("res:" + res2)
})
- 答案是res打印,这是因为catch传入的回调在执行完后,
默认状态依然会是fulfilled
的;
那么如果我们希望后续继续执行catch,那么需要抛出一个异常:
const promise = new Promise((reslove, reject) => {console.log("promise executor开始执行")reject(111)
})
promise.catch(res => {console.log("err:" + res)throw new Errlr("error message")
}).catch(res => {console.log("err2:" + res)
}).then(res2 => {console.log("res:" + res2)
})
const promise = new Promise((resolve, reject) => {// reject("error: aaaaa")resolve("aaaaaa")
})// 1.catch方法也会返回一个新的Promise
// promise.catch(err => {
// console.log("catch回调:", err)
// return "bbbbb"
// }).then(res => {
// console.log("then第一个回调:", res)
// return "ccccc"
// }).then(res => {
// console.log("then第二个回调:", res)
// })// 2.catch方法的执行时机
promise.then(res => {console.log("then第一次回调:", res)// throw new Error("第二个Promise的异常error") return "bbbbbb"
}).then(res => {console.log("then第二次回调:", res)throw new Error("第三个Promise的异常error")
}).then(res => {console.log("then第三次回调:", res)
}).catch(err => {console.log("catch回调被执行:", err)
})// 中断函数继续执行:
// 方式一: return
// 方式二: throw new Error()
// 方式三: yield 暂停(暂时性的中断)
五、Promise实例方法
1.finally方法
finally是在ES9
(ES2018)中新增的一个特性:表示无论Promise对象无论变成fulfilled还是rejected状态,最终都会被执行
的代码。
finally方法是不接收参数的,因为无论前面是fulfilled状态,还是rejected状态,它都会执行。
const promise = new Promise((resolve, reject) => {// pending// fulfilledresolve("aaaa")// rejected// reject("bbbb")
})promise.then(res => {console.log("then:", res)// foo()
}).catch(err => {console.log("catch:", err)// foo()
}).finally(() => {console.log("哈哈哈哈")console.log("呵呵呵呵")
})function foo() {console.log("哈哈哈哈")console.log("呵呵呵呵")
}
六、Promise的类方法
1.resolve方法
前面我们学习的then、catch、finally方法都属于Promise的实例方法,都是存放在Promise的prototype上的。
- 下面我们再来学习一下Promise的
类方法
。
有时候我们已经有一个现成的内容了,希望将其转成Promise来使用,这个时候我们可以使用 Promise.resolve
方法来完成。
- Promise.resolve的用法相当于
new Promise
,并且执行resolve操作:
Promise.resolve("codermq")
// 等价于
new Promise(resolve => resolve("codermq"))
resolve参数的形态:
- 情况一:参数是一个普通的值或者对象
- 情况二:参数本身是Promise
- 情况三:参数是一个thenable
2.reject方法
reject方法类似于resolve方法,只是会将Promise对象的状态设置为reject状态。
Promise.reject的用法相当于new Promise,只是会调用reject:
Promise.reject传入的参数无论是什么形态,都会直接作为reject状态的参数传递到catch的。
// 类方法
const promise = Promise.reject("rejected error")
promise.catch(err => {console.log("err:", err)
})
// 相当于
// new Promise((_, reject) => {
// reject("rejected error")
// })
3.all方法
另外一个类方法是Promise.all:
它的作用是将多个Promise包裹在一起形成一个新的Promise
;
新的Promise状态由包裹的所有Promise共同决定:
- 当所有的Promise状态变成fulfilled状态时,新的Promise状态为fulfilled,并且会将所有Promise的返回值组成一个数组;
- 当有一个Promise状态为reject时,新的Promise状态为reject,并且会将第一个reject的返回值作为参数;
// 创建三个Promise
const p1 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p1 resolve")reject("p1 reject error")}, 3000)
})const p2 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p2 resolve")}, 2000)
})const p3 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p3 resolve")}, 5000)
})// all:全部/所有
Promise.all([p1, p2, p3]).then(res => {console.log("all promise res:", res)
}).catch(err => {console.log("all promise err:", err)
})
4.allSettled方法
all方法有一个缺陷:当有其中一个Promise变成reject状态时,新Promise就会立即变成对应的reject状态。
- 那么对于resolved的,以及依然处于pending状态的Promise,我们是
获取不到对应的结果
的;
在ES11(ES2020)中,添加了新的API Promise.allSettled:
- 该方法会在所有的Promise都有结果(settled),无论是fulfilled,还是rejected时,才会有最终的状态;
- 并且这个Promise的结果一定是fulfilled的;
我们来看一下打印的结果:
- allSettled的结果是一个数组,数组中存放着每一个Promise的结果,并且是对应一个对象的;
- 这个对象中
包含status状态
,以及对应的value值;
// 创建三个Promise
const p1 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p1 resolve")reject("p1 reject error")}, 3000)
})const p2 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p2 resolve")}, 2000)
})const p3 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p3 resolve")}, 5000)
})// 类方法: allSettled
Promise.allSettled([p1, p2, p3]).then(res => {console.log("all settled:", res)
})
5.race方法
如果有一个Promise有了结果,我们就希望决定最终新Promise的状态,那么可以使用race方法:
- race是竞技、竞赛的意思,表示多个Promise相互竞争,谁先有结果,那么就使用谁的结果;
// 创建三个Promise
const p1 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p1 resolve")// reject("p1 reject error")}, 3000)
})const p2 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p2 resolve")reject("p2 reject error")}, 2000)
})const p3 = new Promise((resolve, reject) => {setTimeout(() => {resolve("p3 resolve")}, 5000)
})// 类方法: race方法
// 特点: 会等到一个Promise有结果(无论这个结果是fulfilled还是rejected)
Promise.race([p1, p2, p3]).then(res => {console.log("race promise:", res)
}).catch(err => {console.log("race promise err:", err)
})
6.any方法
any方法是ES12中新增的方法,和race方法是类似的:
- any方法会
等到一个fulfilled状态
,才会决定新Promise的状态; - 如果所有的Promise都是reject的,那么也会等到所有的Promise都变成rejected状态;
如果所有的Promise都是reject的,那么会报一个AggregateError
的错误。
// 创建三个Promise
const p1 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p1 resolve")reject("p1 reject error")}, 3000)
})const p2 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p2 resolve")reject("p2 reject error")}, 2000)
})const p3 = new Promise((resolve, reject) => {setTimeout(() => {// resolve("p3 resolve")reject("p3 reject error")}, 5000)
})// 类方法: any方法
Promise.any([p1, p2, p3]).then(res => {console.log("any promise res:", res)
}).catch(err => {console.log("any promise err:", err)
})
相关文章:
Promise用法详解
文章目录 一、异步代码的困境1.异步任务的处理 二、认识Promise作用1.什么是Promise呢?2.Promise的代码结构 三、Promise状态变化1.Executor2.resolve不同值的区别3.then方法 – 接受两个参数4.then方法 – 多次调用5.then方法 – 返回值6.catch方法 – 多次调用7.c…...

7.spark sql编程
概述 spark 版本为 3.2.4,注意 RDD 转 DataFrame 的代码出现的问题及解决方案 本文目标如下: RDD ,Datasets,DataFrames 之间的区别入门 SparkSession创建 DataFramesDataFrame 操作编程方式运行 sql 查询创建 DatasetsDataFrames 与 RDDs 互相转换 使用…...

【2023】COMAP美赛数模中的大型语言模型LLM和生成式人工智能工具的使用
COMAP比赛中的大型语言模型和生成式人工智能工具的使用 写在最前面GitHub Copilot工具 说明局限性 团队指南引文和引用说明人工智能使用报告 英文原版 Use of Large Language Models and Generative AI Tools in COMAP ContestslimitationsGuidance for teamsCitation and Refe…...
数据结构-顺序表学习资料
什么是顺序表? 顺序表是一种线性数据结构,它按照元素在内存中的物理顺序存储数据。顺序表可以通过数组实现,也可以通过链表和动态数组实现。 顺序表的特点 元素连续存储:顺序表中的元素在内存中是连续存储的,这样可…...

微信小程序获取剪切板的内容到输入框中
xml代码 <navigation-bar title"Weixin" back"{{false}}" color"black" background"#FFF"></navigation-bar> <view><input placeholder"请输入内容" name"content" type"text" …...

【年底不想背锅!网络工程师必收藏的排障命令大全】
网络故障排除工具是每个网络工程师的必需品。 为了提升我们的工作效率, 不浪费时间,工具的重要性显而易见 特别是每当添加新的设备或网络发生变更时,新的问题就会出现,而且很难快速确定问题出在哪里。每一位网络工程师或从事网…...
Windows服务器用PowerShell script判断服务器启动时间并做reboot动作
脚本如下,Windows 2019环境 60*119 是119分钟 $x(Get-Date) - (gcim Win32_OperatingSystem).LastBootUpTime echo $x.TotalSeconds " seconds passed" if($x.TotalSeconds -gt 60*119) {Invoke-Expression -Command "msg.exe * /TIME:20 reboot i…...

【HTML】播放器如何自动播放【已解决】
自动播放器策略 先了解浏览器的自动播放器策略 始终允许静音自动播放在以下情况,带声音的自动播放才会被允许 2.1 用户已经与当前域进行交互 2.2 在桌面上,用户的媒体参与指数阈值(MEI)已被越过,这意味着用户以前播放带有声音的视频。 2.3 …...

Go Gin中间件
Gin是一个用Go语言编写的Web框架,它提供了一种简单的方式来创建HTTP路由和处理HTTP请求。中间件是Gin框架中的一个重要概念,它可以用来处理HTTP请求和响应,或者在处理请求之前和之后执行一些操作。 以下是关于Gin中间件开发的一些基本信息&am…...

财务数字化转型的切入点是什么?_光点科技
随着科技的不断进步,数字化转型已经成为各个行业追求的目标,财务领域也不例外。那么,财务数字化转型的切入点在哪里呢?如何确保转型的成功进行? 数据整合与管理 财务数据的准确性与及时性是财务管理的基石。数字化转型…...

Langchain知识点(上)
输出格式 Pydantic (JSON) 解析器 # 创建模型实例 from langchain import OpenAI model OpenAI(model_nametext-davinci-003)# ------Part 2 # 创建一个空的DataFrame用于存储结果 import pandas as pd df pd.DataFrame(columns["flower_type", "price"…...

Tomcat安装配置教程
目录 1、安装tomcat1.1、查看JDK版本1.2、 匹配对应的JDK版本1.3、 下载Tomcat1.3.1、 安装包版(推荐,不用配环境)1.3.2、 压缩包版 2、 运行Tomcat3、 不能运行问题 1、安装tomcat 1.1、查看JDK版本 由于不同版本tomcat对于jdk的版本有要求…...

Python小试牛刀:GUI(图形界面)实现计算器UI界面(三)
上一篇:Python小试牛刀:GUI(图形界面)实现计算器UI界面(二)-CSDN博客 回顾前两篇文章,第一篇文章主要实现了计算器UI界面如何布局,以及简单概述Python常用的GUI库。第二篇文章主要实现了计算器UI界面按钮组…...

王道计算机网络
一、计算机网络概述 (一)计算机网络基本概念 计算机网络的定义、组成与功能 定义:以能够相互共享资源的方式互连起来的自治计算机系统的集合。 目的:资源共享, 组成单元:自治、互不影响的计算机 网络协议 从不同角度计算机网络…...

【漏洞复现】IIS_7.o7.5解析漏洞
感谢互联网提供分享知识与智慧,在法治的社会里,请遵守有关法律法规 文章目录 1.1、漏洞描述1.2、漏洞等级1.3、影响版本1.4、漏洞复现1、基础环境2、漏洞扫描3、漏洞验证 1.5、修复建议 1.1、漏洞描述 漏洞原理: cgi.fix_path1 1.png/.php该…...

Java 高效生成按指定间隔连续递增的列表(int,double)
简介 Java 按照指定间隔生成连续递增的List 列表(引入Stream 类和流操作来提高效率): 1. 生成递增的List< Integer> Testpublic void test009(){int start 1;int interval 2;int count 10;List<Integer> list IntStream.ite…...

C++ reference
cppreference.com 《现代C语言核心特性解析》 这是一本 C 进阶图书,全书分为 42 章,深入探讨了从 C11 到 C20 引入的核心特性。 本书不仅通过大量的实例代码讲解特性的概念和语法,还从编译器的角度分析特性的实现原理,让读者…...

关于网站安全的一些讨论
互联网的普及和发展为企业和个人提供了巨大的机会,但同时也伴随着网络安全威胁的增加。网站被攻击是一个常见的问题,可能导致数据泄露、服务中断和声誉受损。在本文中,我们将探讨与网络安全紧密相关的因素,分析为什么网站容易受到…...
unity 截图
unity 截图适用于各分辨率 float scr;void Start(){scr Screen.width /2160.00f;//2160是我做程序时的分辨率 Screen.width为打包后机器的分辨率}/// <summary>/// 区域截图/// </summary>/// <param name"rectT"></param>/// <param …...

浏览器无图模式省流量经验
【备注】本文适合于那些用自购上网卡(非单位报销)、流量费花的心痛、平日里抠抠搜搜的diaosi人群!流量自由人群请关闭退出! 近日图年包流量费便宜,从某东平台上买了一个号称新款usb上网卡,只用了2天时间&a…...

MPNet:旋转机械轻量化故障诊断模型详解python代码复现
目录 一、问题背景与挑战 二、MPNet核心架构 2.1 多分支特征融合模块(MBFM) 2.2 残差注意力金字塔模块(RAPM) 2.2.1 空间金字塔注意力(SPA) 2.2.2 金字塔残差块(PRBlock) 2.3 分类器设计 三、关键技术突破 3.1 多尺度特征融合 3.2 轻量化设计策略 3.3 抗噪声…...
conda相比python好处
Conda 作为 Python 的环境和包管理工具,相比原生 Python 生态(如 pip 虚拟环境)有许多独特优势,尤其在多项目管理、依赖处理和跨平台兼容性等方面表现更优。以下是 Conda 的核心好处: 一、一站式环境管理:…...
云原生核心技术 (7/12): K8s 核心概念白话解读(上):Pod 和 Deployment 究竟是什么?
大家好,欢迎来到《云原生核心技术》系列的第七篇! 在上一篇,我们成功地使用 Minikube 或 kind 在自己的电脑上搭建起了一个迷你但功能完备的 Kubernetes 集群。现在,我们就像一个拥有了一块崭新数字土地的农场主,是时…...

Prompt Tuning、P-Tuning、Prefix Tuning的区别
一、Prompt Tuning、P-Tuning、Prefix Tuning的区别 1. Prompt Tuning(提示调优) 核心思想:固定预训练模型参数,仅学习额外的连续提示向量(通常是嵌入层的一部分)。实现方式:在输入文本前添加可训练的连续向量(软提示),模型只更新这些提示参数。优势:参数量少(仅提…...

突破不可导策略的训练难题:零阶优化与强化学习的深度嵌合
强化学习(Reinforcement Learning, RL)是工业领域智能控制的重要方法。它的基本原理是将最优控制问题建模为马尔可夫决策过程,然后使用强化学习的Actor-Critic机制(中文译作“知行互动”机制),逐步迭代求解…...

【大模型RAG】Docker 一键部署 Milvus 完整攻略
本文概要 Milvus 2.5 Stand-alone 版可通过 Docker 在几分钟内完成安装;只需暴露 19530(gRPC)与 9091(HTTP/WebUI)两个端口,即可让本地电脑通过 PyMilvus 或浏览器访问远程 Linux 服务器上的 Milvus。下面…...
OkHttp 中实现断点续传 demo
在 OkHttp 中实现断点续传主要通过以下步骤完成,核心是利用 HTTP 协议的 Range 请求头指定下载范围: 实现原理 Range 请求头:向服务器请求文件的特定字节范围(如 Range: bytes1024-) 本地文件记录:保存已…...
生成 Git SSH 证书
🔑 1. 生成 SSH 密钥对 在终端(Windows 使用 Git Bash,Mac/Linux 使用 Terminal)执行命令: ssh-keygen -t rsa -b 4096 -C "your_emailexample.com" 参数说明: -t rsa&#x…...
如何为服务器生成TLS证书
TLS(Transport Layer Security)证书是确保网络通信安全的重要手段,它通过加密技术保护传输的数据不被窃听和篡改。在服务器上配置TLS证书,可以使用户通过HTTPS协议安全地访问您的网站。本文将详细介绍如何在服务器上生成一个TLS证…...
HTML前端开发:JavaScript 常用事件详解
作为前端开发的核心,JavaScript 事件是用户与网页交互的基础。以下是常见事件的详细说明和用法示例: 1. onclick - 点击事件 当元素被单击时触发(左键点击) button.onclick function() {alert("按钮被点击了!&…...