springCloud组件专题(五) --- seata

embedded/2024/9/18 12:37:54/ 标签: spring cloud, spring, 后端, seata, 面试, 分布式事务

一.Seata介绍

        1. seata是什么

是一款开源的分布式事务解决方案,供了 AT、TCC、SAGA 和 XA 事务模式。

        2.分布式事务中的概念

                2.1. 二阶段提交

二阶段提交的含义就是将事务的提交分成两个步骤,分别为:

                准备阶段:事务协调者询问所有参与者是否准备好提交或者回滚事务,并等待它们的响应。(注意,等待响应一般会设置时间,利用超时进行事务回退是常见的一种方式)

                提交阶段:如果所有参与者都准备好提交,事务协调者通知它们提交事务;如果有任何一个参与者未能准备好或者出现错误,事务协调者通知它们回滚事务.

                二阶段提交中,从第一阶段的准备阶段,业务所涉及的数据就被锁定,并且锁定跨越整个提交流程。在高并发和涉及业务模块较多的情况下 对数据库的性能影响较大,但是它提供了解决分布式系统下数据一致性问题的思路

                2.2.三阶段提交

                三阶段提交是对两阶段提交的改进,通过在第一阶段引入额外的准备阶段来解决某些情况下的阻塞问题。在三阶段提交中,除了准备和提交阶段外,还有一个称为“预提交”或“预准备”阶段,用于减少参与者在第二阶段的等待时间

                2.3.TC,TM,RM

                TC (Transaction Coordinator) - 事务协调者​

维护全局和分支事务的状态,驱动全局事务提交或回滚。对于我们使用seata来说,TC就是我们部署的seata服务端、

                TM (Transaction Manager) - 事务管理器​

定义全局事务的范围:开始全局事务、提交或回滚全局事务。seata的AT,XA模式中,TM可以片面的理解成加了@GlobalTransactional的方法的代理类(这个例子为了方便大家理解,并不完全准确)。

                RM (Resource Manager) - 资源管理器​

管理分支事务处理的资源,与TC交谈以注册分支事务和报告分支事务的状态,并驱动分支事务提交或回滚。seata的AT,XA模式中,RM可以理解成datasource(这个例子为了方便大家理解,并不完全准确)。

        3.XA,AT,TCC,SAGA概念

                3.1. XA

                Seata XA 模式是利用事务资源(数据库、消息服务等)对 XA 协议的支持,以 XA 协议的机制来管理分支事务的一种事务模式,简单来说,就是seata作为一个协调者,借助数据库本身的能力进行分布式事务管理。

具体工作机制参见官网:

Seata XA 模式 | Apache Seata

                3.2. AT

                AT 模式是 Seata 的一种非侵入式的分布式事务解决方案,代码层面来讲,只需要一个注解就可以实现分布式事务管理,使用AT模式时候,我们操作数据库实际上用的是 Seata 自带的数据源代理 DataSourceProxy,Seata 在这层代理中加入了很多逻辑,比如插入回滚 undo_log 日志,检查全局锁等。简单来讲,AT将事务分成两阶段:

一阶段:业务数据和回滚日志记录在同一个本地事务中提交,释放本地锁和连接资源

二阶段:无异常,提交异步化,非常快速地完成。有异常,滚通过一阶段的回滚日志进行补偿。

具体的读写隔离的原理参考官网:

https://seata.apache.org/zh-cn/docs/dev/mode/at-mode

                3.3. TCC

                TCC 模式是 Seata 支持的一种由业务方细粒度控制的侵入式分布式事务解决方案,其分布式事务模型直接作用于服务层,不依赖底层数据库。

                从代码角度讲就是,TCC需要我们不仅要自己写业务代码,还要写失败的补偿代码,成功的提交代码。这样带来的好处就是,不仅能支持关系型数据库,还能支持redis,三方调用等任何方式的数据层修改。

具体执行模型见官网:

Seata TCC 模式 | Apache Seata

                3.4.SAGA

                SAGA官方说法是支持长事务的一种模式,其实简单来理解,它是流程+TCC的结合。在使用上,我们需要先定义状态机,然后对每个步骤进行编码。

其原理详见官网:

Seata Saga 模式 | Apache Seata

二.Seata-Server 搭建

2.1. Seata-Server下载

官方下载地址:https://github.com/seata/seata/releases

下载完成之后需要解压

2.2. Seata-Server配置

2.2.1. 需要打开conf目录
2.2.2. 配置registry.conf文件

这个文件用来管理seata服务的注册,我们修改Seata的注册中心和配置中心为Nacos

** 配置文件里一堆东西都不用管,type指定了nacos,只修改nacos的就行 ** 

registry {# file 、nacos 、eureka、redis、zk、consul、etcd3、sofatype = "nacos"# type  指定了nacos,这里我们只需要管nacos的配置就行  后面的config也是nacos {application = "seata-server"serverAddr = "127.0.0.1:8848"group = "SEATA_GROUP"namespace = ""cluster = "default"username = ""password = ""}eureka {serviceUrl = "http://localhost:8761/eureka"application = "default"weight = "1"}redis {serverAddr = "localhost:6379"db = 0password = ""cluster = "default"timeout = 0}zk {cluster = "default"serverAddr = "127.0.0.1:2181"sessionTimeout = 6000connectTimeout = 2000username = ""password = ""}consul {cluster = "default"serverAddr = "127.0.0.1:8500"aclToken = ""}etcd3 {cluster = "default"serverAddr = "http://localhost:2379"}sofa {serverAddr = "127.0.0.1:9603"application = "default"region = "DEFAULT_ZONE"datacenter = "DefaultDataCenter"cluster = "default"group = "SEATA_GROUP"addressWaitTime = "3000"}file {name = "file.conf"}
}config {# file、nacos 、apollo、zk、consul、etcd3type = "nacos"# type  指定了nacos,这里我们只需要管nacos的配置就行# 注意,这里指定了一个配置文件,叫做 seataServer.propertiesnacos {serverAddr = "127.0.0.1:8848"namespace = ""group = "SEATA_GROUP"username = ""password = ""dataId = "seataServer.properties"}consul {serverAddr = "127.0.0.1:8500"aclToken = ""}apollo {appId = "seata-server"## apolloConfigService will cover apolloMetaapolloMeta = "http://192.168.1.204:8801"apolloConfigService = "http://192.168.1.204:8080"namespace = "application"apolloAccesskeySecret = ""cluster = "seata"}zk {serverAddr = "127.0.0.1:2181"sessionTimeout = 6000connectTimeout = 2000username = ""password = ""nodePath = "/seata/seata.properties"}etcd3 {serverAddr = "http://localhost:2379"}file {name = "file.conf"}
}

2.2.3. 修改file.conf

这个文件管理Seata的存储模式。
        Server端存储模式(store.mode)支持三种:
                1. file:单机模式,全局事务会话信息内存中读写并持久化本地文件root.data,性能较高(默认)
                2. DB:高可用模式,全局事务会话信息通过DB共享,相对性能差一些
                3. redis:Seata-Server1.3及以上版本支持,性能较高,存在事务信息丢失风险,需要配合实际场景使用。


我们把Seata的默认存储模式修改为数据库"DB",同时需要配置JDBC 如下:

## transaction log store, only used in seata-server
store {## store mode: file、db、redismode = "db"## rsa decryption public keypublicKey = ""## file store propertyfile {## store location dirdir = "sessionStore"# branch session size , if exceeded first try compress lockkey, still exceeded throws exceptionsmaxBranchSessionSize = 16384# globe session size , if exceeded throws exceptionsmaxGlobalSessionSize = 512# file buffer size , if exceeded allocate new bufferfileWriteBufferCacheSize = 16384# when recover batch read sizesessionReloadReadSize = 100# async, syncflushDiskMode = async}## database store propertydb {## the implement of javax.sql.DataSource, such as DruidDataSource(druid)/BasicDataSource(dbcp)/HikariDataSource(hikari) etc.datasource = "druid"## mysql/oracle/postgresql/h2/oceanbase etc.dbType = "mysql"driverClassName = "com.mysql.jdbc.Driver"## if using mysql to store the data, recommend add rewriteBatchedStatements=true in jdbc connection paramurl = "jdbc:mysql://localhost:3306/seata?useUnicode=true&characterEncoding=UTF-8"user = "root"password = "root"minConn = 5maxConn = 100globalTable = "global_table"branchTable = "branch_table"lockTable = "lock_table"queryLimit = 100maxWait = 5000}## redis store propertyredis {## redis mode: single、sentinelmode = "single"## single mode propertysingle {host = "127.0.0.1"port = "6379"}## sentinel mode propertysentinel {masterName = ""## such as "10.28.235.65:26379,10.28.235.65:26380,10.28.235.65:26381"sentinelHosts = ""}password = ""database = "0"minConn = 1maxConn = 10maxTotal = 100queryLimit = 100}
}

数据库中,我们需要建几个seata的表
建表语句地址:https://github.com/seata/seata/blob/develop/script/server/db/mysql.sql
- global_table :  全局事务会话表
- branch_table:  分支事务会话表
- lock_table:       锁数据表

也可以从我这里粘:

-- the table to store GlobalSession data
CREATE TABLE IF NOT EXISTS `global_table`
(`xid`                       VARCHAR(128) NOT NULL,`transaction_id`            BIGINT,`status`                    TINYINT      NOT NULL,`application_id`            VARCHAR(32),`transaction_service_group` VARCHAR(32),`transaction_name`          VARCHAR(128),`timeout`                   INT,`begin_time`                BIGINT,`application_data`          VARCHAR(2000),`gmt_create`                DATETIME,`gmt_modified`              DATETIME,PRIMARY KEY (`xid`),KEY `idx_gmt_modified_status` (`gmt_modified`, `status`),KEY `idx_transaction_id` (`transaction_id`)
) ENGINE = InnoDBDEFAULT CHARSET = utf8;-- the table to store BranchSession data
CREATE TABLE IF NOT EXISTS `branch_table`
(`branch_id`         BIGINT       NOT NULL,`xid`               VARCHAR(128) NOT NULL,`transaction_id`    BIGINT,`resource_group_id` VARCHAR(32),`resource_id`       VARCHAR(256),`branch_type`       VARCHAR(8),`status`            TINYINT,`client_id`         VARCHAR(64),`application_data`  VARCHAR(2000),`gmt_create`        DATETIME(6),`gmt_modified`      DATETIME(6),PRIMARY KEY (`branch_id`),KEY `idx_xid` (`xid`)
) ENGINE = InnoDBDEFAULT CHARSET = utf8;-- the table to store lock data
CREATE TABLE IF NOT EXISTS `lock_table`
(`row_key`        VARCHAR(128) NOT NULL,`xid`            VARCHAR(128),`transaction_id` BIGINT,`branch_id`      BIGINT       NOT NULL,`resource_id`    VARCHAR(256),`table_name`     VARCHAR(32),`pk`             VARCHAR(36),`status`         TINYINT      NOT NULL DEFAULT '0' COMMENT '0:locked ,1:rollbacking',`gmt_create`     DATETIME,`gmt_modified`   DATETIME,PRIMARY KEY (`row_key`),KEY `idx_status` (`status`),KEY `idx_branch_id` (`branch_id`)
) ENGINE = InnoDBDEFAULT CHARSET = utf8;
2.2.4.nacos配置中心替换file.conf 

本地启动可以不做这一步,seata集群,或者企业项目,一般会用nacos的配置中心而非本地file.conf文件

在1.2.2中,我们进行了nacos的配置,其中有一个config{ dataId: "xxxx" }

我们可以在配置中心的配置管理里,加一个对应的配置,来使用配置中心而非本地文件配置

内容如下:

#For details about configuration items, see https://seata.io/zh-cn/docs/user/configurations.html
#Transport configuration, for client and server
transport.type=TCP
transport.server=NIO
transport.heartbeat=true
transport.enableTmClientBatchSendRequest=false
transport.enableRmClientBatchSendRequest=true
transport.enableTcServerBatchSendResponse=false
transport.rpcRmRequestTimeout=30000
transport.rpcTmRequestTimeout=30000
transport.rpcTcRequestTimeout=30000
transport.threadFactory.bossThreadPrefix=NettyBoss
transport.threadFactory.workerThreadPrefix=NettyServerNIOWorker
transport.threadFactory.serverExecutorThreadPrefix=NettyServerBizHandler
transport.threadFactory.shareBossWorker=false
transport.threadFactory.clientSelectorThreadPrefix=NettyClientSelector
transport.threadFactory.clientSelectorThreadSize=1
transport.threadFactory.clientWorkerThreadPrefix=NettyClientWorkerThread
transport.threadFactory.bossThreadSize=1
transport.threadFactory.workerThreadSize=default
transport.shutdown.wait=3
transport.serialization=seata
transport.compressor=none#Transaction routing rules configuration, only for the client
service.vgroupMapping.default_tx_group=default#Transaction rule configuration, only for the client
client.rm.asyncCommitBufferLimit=10000
client.rm.lock.retryInterval=10
client.rm.lock.retryTimes=30
client.rm.lock.retryPolicyBranchRollbackOnConflict=true
client.rm.reportRetryCount=5
client.rm.tableMetaCheckEnable=true
client.rm.tableMetaCheckerInterval=60000
client.rm.sqlParserType=druid
client.rm.reportSuccessEnable=false
client.rm.sagaBranchRegisterEnable=false
client.rm.sagaJsonParser=fastjson
client.rm.tccActionInterceptorOrder=-2147482648
client.tm.commitRetryCount=5
client.tm.rollbackRetryCount=5
client.tm.defaultGlobalTransactionTimeout=60000
client.tm.degradeCheck=false
client.tm.degradeCheckAllowTimes=10
client.tm.degradeCheckPeriod=2000
client.tm.interceptorOrder=-2147482648
client.undo.dataValidation=true
client.undo.logSerialization=jackson
client.undo.onlyCareUpdateColumns=true
server.undo.logSaveDays=7
server.undo.logDeletePeriod=86400000
client.undo.logTable=undo_log
client.undo.compress.enable=true
client.undo.compress.type=zip
client.undo.compress.threshold=64k
#For TCC transaction mode
tcc.fence.logTableName=tcc_fence_log
tcc.fence.cleanPeriod=1h#Log rule configuration, for client and server
log.exceptionRate=100#Transaction storage configuration, only for the server. The file, DB, and redis configuration values are optional.
store.mode=db
store.lock.mode=file
store.session.mode=file#If `store.mode,store.lock.mode,store.session.mode` are not equal to `file`, you can remove the configuration block.
store.file.dir=file_store/data
store.file.maxBranchSessionSize=16384
store.file.maxGlobalSessionSize=512
store.file.fileWriteBufferCacheSize=16384
store.file.flushDiskMode=async
store.file.sessionReloadReadSize=100#These configurations are required if the `store mode` is `db`. If `store.mode,store.lock.mode,store.session.mode` are not equal to `db`, you can remove the configuration block.
store.db.datasource=druid
store.db.dbType=mysql
store.db.driverClassName=com.mysql.cj.jdbc.Driver
store.db.url=jdbc:mysql://127.0.0.1:3306/seata?useUnicode=true&rewriteBatchedStatements=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
store.db.user=root
store.db.password=123456
store.db.minConn=5
store.db.maxConn=30
store.db.globalTable=global_table
store.db.branchTable=branch_table
store.db.distributedLockTable=distributed_lock
store.db.queryLimit=100
store.db.lockTable=lock_table
store.db.maxWait=5000#Transaction rule configuration, only for the server
server.recovery.committingRetryPeriod=1000
server.recovery.asynCommittingRetryPeriod=1000
server.recovery.rollbackingRetryPeriod=1000
server.recovery.timeoutRetryPeriod=1000
server.maxCommitRetryTimeout=-1
server.maxRollbackRetryTimeout=-1
server.rollbackRetryTimeoutUnlockEnable=false
server.distributedLockExpireTime=10000
server.xaerNotaRetryTimeout=60000
server.session.branchAsyncQueueSize=5000
server.session.enableBranchAsyncRemove=false
server.enableParallelRequestHandle=false#Metrics configuration, only for the server
metrics.enabled=false
metrics.registryType=compact
metrics.exporterList=prometheus
metrics.exporterPrometheusPort=9898

每个属性的含义可以在seata官网查到,太多了这里就不一个个介绍了

2.3. 启动

启动步骤为,先启动nacos然后在启动Seata-Server

启动Seata-Server的方式非常简单,直接双击此文件即可:seata-server-1.4.2\bin\seata-server.bat

linux的话运行.sh

启动完成效果

然后在nacos控制台上就可以看到Seata-Server

三.微服务项目集成

3.1. 引入依赖

<dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-seata</artifactId>
</dependency>

3.2. 配置TC(Seata-server)地址

seata:registry: # TC服务注册中心的配置,微服务根据这些信息去注册中心获取tc服务地址# 参考tc服务自己的registry.conf中的配置type: nacosnacos: # 用于在nacos中寻找tcserver-addr: 127.0.0.1:8848namespace: ""group: SEATA_GROUP  # 分组名要入registry.conf中的配置一致application: seata-tc-server # tc服务在nacos中的服务名称cluster: SH                  # 对应TC的配置tx-service-group: seata-demo # 事务组,根据这个获取tc服务的cluster名称service:vgroup-mapping: # 事务组与TC服务cluster的映射关系seata-demo: SH

3.3. 模式配置

        3.3.1. 使用XA模式

        XA模式是通过数据库的支持达到事务的。使用xa模式,需要两个条件

        1,数据库本身支持XA事务

        2,java程序通过jdbc访问数据库

        需要进行的配置如下:

        step1: yml配置文件中增加配置:

seata:data-source-proxy-mode: XA

        step2:要使用事务的方法上加 @GlobalTransactional

@Service
public class BusinessService {@GlobalTransactionalpublic void doBusiness() {// 执行本地事务// ...// 调用远程服务// ...}
}

        3.3.2. 使用AT模式

        AT模式的本质是Seata 的 JDBC 数据源代理通过对业务 SQL 的解析,把业务数据在更新前的数据镜像组织成回滚日志,利用 本地事务的 ACID 特性,将业务数据的更新和回滚日志的写入在同一个本地事务中提交。

        具体操作步骤如下:

        step1: yml配置文件中增加配置:

seata:data-source-poxy-mode: AT

        step2:每个服务的数据库增加一个表:

CREATE TABLE `undo_log` (`id` bigint(20) NOT NULL AUTO_INCREMENT,`branch_id` bigint(20) NOT NULL,`xid` varchar(100) NOT NULL,`context` varchar(128) NOT NULL,`rollback_info` longblob NOT NULL,`log_status` int(11) NOT NULL,`log_created` datetime NOT NULL,`log_modified` datetime NOT NULL,`ext` varchar(100) DEFAULT NULL,PRIMARY KEY (`id`),UNIQUE KEY `ux_undo_log` (`xid`,`branch_id`)
) 

        step3:Service层增加注解

@Service
public class BusinessService {@GlobalTransactionalpublic void doBusiness() {// 执行本地事务// ...// 调用远程服务// ...}
}

        3.3.2. 使用TCC模式

        TCC是比较复杂的一个事务模式,它不依赖于底层数据资源的事务支持,且Try-Confirm-Cancel三者完全由开发者自行开发定义:

  • 一阶段 prepare 行为:调用 自定义 的 Try逻辑。
  • 二阶段 commit 行为:调用 自定义的 Confirm 逻辑。
  • 二阶段 rollback 行为:调用 自定义的 Cancel 逻辑

        当服务中涉及如下情况,则可考虑使用TCC模式:

  • 不支持事务的数据库与中间件(如redis)等的操作
  • AT模式暂未支持的数据库(目前AT支持Mysql、Oracle与PostgreSQL)
  • 跨公司服务(第三方服务)的调用(无法共享Seata Server)
  • 跨语言的应用调用
  • 有手动控制整个二阶段提交过程的需求

        **我实际做过的项目里,没有使用TCC的,所以这东西,了解一下就好**

        具体操作步骤如下:

        step1:由于TCC模式不赖数据库事务能力,所以不再需要进行data-source-poxy-mode的配置,yml文件中不需要改东西

        step2:编写两个服务的service,每个service都要手动编写commit,rollback,接口声明如下

服务A的service

public interface serviceOne {@TwoPhaseBusinessAction(name = "prepare", commitMethod = "commit", rollbackMethod = "rollback")public boolean prepare(BusinessActionContext actionContext, @BusinessActionContextParameter(paramName = "a") String a);public boolean commit(BusinessActionContext actionContext);public boolean rollback(BusinessActionContext actionContext);
}

服务B的service

public interface serviceTwo {@TwoPhaseBusinessAction(name = "prepare", commitMethod = "commit", rollbackMethod = "rollback")public boolean prepare(BusinessActionContext actionContext, @BusinessActionContextParameter(paramName = "a") String a);public boolean commit(BusinessActionContext actionContext);public boolean rollback(BusinessActionContext actionContext);
}

        step3:编写业务主方法

@GlobalTransactional
public String doTransactionCommit(){//服务A事务参与者serviceOne.prepare(null,"one");//服务B事务参与者serviceTwo.prepare(null,"two");
}

        3.3.2. 使用SAGA模式

        官方介绍:Saga 模式是 SEATA 提供的长事务解决方案,在 Saga 模式中,业务流程中每个参与者都提交本地事务,当出现某一个参与者失败则补偿前面已经成功的参与者,一阶段正向服务和二阶段补偿服务都由业务开发实现。

        个人理解:saga其实类似TCC,开发者自己来维护事务的提交和失败补偿,但是saga引入了类似流程引擎的东西,通过定义流程来确定成功,失败该使用对应的什么方式来处理,sage可以视作一种TCC的增强(TCC+引擎模板)。

这个模式我没有在实际开发中用过,建议大家看这位大佬的:

springcloud+eureka整合阿里seata-saga模式_51CTO博客_spring cloud>spring cloud整合seata

稍微总结一下,就是

step1:定义状态机(就是一个json文件)

step2:增加三张库表,用于维护状态机状态

step3:类似于TCC模式,自己变成写事务的提交,回滚方法


http://www.ppmy.cn/embedded/88922.html

相关文章

JAVA基础知识点3 (String 和 StringBuffer 以及 StringBuilder 的特点以及区别)

1&#xff0c;String 和 StringBuffer 以及 StringBuilder 的特点 &#xff08;1&#xff09;String的特点&#xff1a;String是final修饰的字符序列是不可改变的&#xff0c; 是字符串常量&#xff0c;一旦初始化就不可以被更改,因此是线程安全的 因为是常量每次对其操作都会…

利用开源可视化报表工具进入流程化办公!

很多客户朋友都希望能实现流程化办公&#xff0c;因为只有这样才能帮助企业顺利降本、增效、提质&#xff0c;利用好企业内部数据资源&#xff0c;打破信息孤岛壁垒&#xff0c;实现高效发展。低代码技术平台、开源可视化报表工具优势功能特点多&#xff0c;是提质高效的办公利…

mac|运行别人的SpringBoot+Vue项目

一、运行vue 1、查看项目版本&#xff0c;在package.json中查看&#xff0c;在dependencies中的vue就是对应的版本 2、查看本机的vue版本&#xff1a;vue -V 3、删除node_modules 、package-lock.json 4、运行npm install 如果卡住不动&#xff0c;可能是因为网络问题&…

[Docker][Docker Container]详细讲解

目录 1.什么是容器&#xff1f;2.容器命令1.docker creatre2.docker run3.docker ps4.docker logs5.docker attach6.docker exec7.docker start8.docker stop9.docker restart10.docker kill11.docker top12.docker stats13.docker container inspect14.docker port15.docker c…

LeeCode Practice Journal | Day31_GA05

56. 合并区间 题目&#xff1a;56. 合并区间 - 力扣&#xff08;LeetCode&#xff09; 题解&#xff1a;代码随想录 (programmercarl.com) 思路很清晰&#xff0c;对数组的操作稀烂&#xff0c;细节上也出现很多问题 solution public class Solution {public int[][] Merge(in…

高级java每日一道面试题-2024年8月03日-web篇-forward和redirect有什么区别?

如果有遗漏,评论区告诉我进行补充 面试官: forward和redirect有什么区别? 我回答: 在Java Web开发中&#xff0c;forward和redirect是Servlet容器提供的两种用于页面跳转的技术。它们的主要区别在于客户端感知的方式、URL地址的变化、请求对象的共享等方面。下面详细介绍两…

2-53 基于matlab的15种图像纹理特征计算

基于matlab的15种图像纹理特征计算。纹理特征包括小梯度优势 T1、大梯度优势 T2、 灰度分布的不均匀性 T3、 梯度分布的不均匀性 T4 、能量 T5、灰度平均 T6、梯度平均 T7、灰度均方差 T8 、梯度均方差 T9、相关 T10 、灰度熵 T11、梯度熵 T12 、 混合熵 T13、惯性 T14 、 逆差…

windows中node版本的切换(nvm管理工具),解决项目兼容问题 node版本管理、国内npm源镜像切换(保姆级教程,值得收藏)

前言 在工作中&#xff0c;我们可能同时在进行2个或者多个不同的项目开发&#xff0c;每个项目的需求不同&#xff0c;进而不同项目必须依赖不同版本的NodeJS运行环境&#xff0c;这种情况下&#xff0c;对于维护多个版本的node将会是一件非常麻烦的事情&#xff0c;nvm就是为…

vscode安装与配置本地c/c++编译调试环境

目录 &#xff08;1&#xff09;安装vscode和常用插件 1.下载安装vscode 2.安装常用插件 &#xff08;2&#xff09;本地安装和配置编译器 1.安装编译器 2.vscode配置编译器 第1种&#xff1a;全局配置 第2种&#xff1a;为当前项目个性化配置 &#xff08;3&#xff…

数论第四节:二元一次不定方程、勾股数

不定方程定义 解不确定的方程称为不定方程。一般化的定义为&#xff1a;不定方程是指未知数的个数多余方程的个数&#xff0c;或未知数受到某种限制&#xff08;如整数、正整数等&#xff09;的方程和方程组。 二元一次不定方程定义 形如axbyc的形式的方程。其中a,b不等于0&…

Elasticsearch简介

一、Elasticsearch简介 Elasticsearch是一个基于Lucene的搜索服务器&#xff0c;它提供了一个分布式、多租户的全文搜索引擎&#xff0c;能够实时地存储、检索和分析大规模的数据。Elasticsearch不仅支持全文搜索&#xff0c;还提供了结构化搜索、数据分析、复杂的语言处理、地…

《LeetCode热题100》---<5.③普通数组篇五道>

本篇博客讲解LeetCode热题100道普通数组篇中的五道题 第五道&#xff1a;缺失的第一个正数&#xff08;困难&#xff09; 第五道&#xff1a;缺失的第一个正数&#xff08;困难&#xff09; 方法一&#xff1a;将数组视为哈希表 class Solution {public int firstMissingPosi…

浅谈基础的图算法——最小生成树算法(c++)

文章目录 前置知识图存图方法邻接矩阵邻接链表&#xff08;链式前向星&#xff09;&#xff08;网络流必备&#xff09;vector&#xff08;简单&#xff0c;快&#xff09; 最小生成树模板题【模板】最小生成树题目描述输入格式输出格式样例 #1样例输入 #1样例输出 #1 提示 AC代…

Redis 数据结构深度解析:跳跃表(Skiplist)

引言 在高性能数据库和内存缓存系统中&#xff0c;数据结构的选择关乎到系统整体性能的优劣。Redis&#xff0c;作为一款广泛使用的高性能键值存储系统&#xff0c;其内部大量采用了一种名为“跳跃表&#xff08;Skiplist&#xff09;”的数据结构&#xff0c;用以实现有序数据…

vlunstack-1(横向,phpmyadmin拿shell,xycms拿shell,cs和msf联动)

Vulnstack-1 内网环境搭建 环境配置&#xff1a; 靶机介绍 包括win7的web端&#xff0c;还有win2003为域成员&#xff0c;域控为win2008 win7内网ip&#xff1a;192.168.157.153 外网ip&#xff1a;192.168.52.143 域成员 win2003 ip 192.168.52.141 域控 win2008 ip 192.168…

常用命令git branch

Git Branch 命令总结 列出分支 git branch&#xff1a;显示本地分支&#xff0c;当前分支会被标记。git branch -r&#xff1a;显示远程分支。git branch -a&#xff1a;显示所有本地和远程分支。 创建分支 git branch <branch_name>&#xff1a;创建一个新分支但不自…

批发行业手机开单-手机开单 源码CyberWinApp-SAAS 本地化及未来之窗行业应用跨平台架构

一、saas本地化优势 它的优点令人瞩目&#xff1a; 其一&#xff0c;访问速度似闪电&#xff0c;瞬间呈现精彩内容&#xff0c;让您告别漫长等待&#xff0c;就像在信息高速公路上驾驶着超级跑车&#xff0c;一路畅行无阻。 其二&#xff0c;摆脱网络束缚&#xff0c;不受网络…

sdwan

分支互联网络解决方案 - 华为企业业务 分支互联网络解决方案 随着5G、AI、物联网等新兴技术与云紧密结合&#xff0c;企业业务智能化和云化加速。 企业分支WAN流量激增&#xff0c;传统以MPLS专线为主的广域互联网络难以支撑业务发展。SD-WAN成为应对云时代的必然选择。 SD…

大语言模型(LLM)快速理解

自2022年&#xff0c;ChatGPT发布之后&#xff0c;大语言模型&#xff08;Large Language Model&#xff09;&#xff0c;简称LLM掀起了一波狂潮。作为学习理解LLM的开始&#xff0c;先来整体理解一下大语言模型。 一、发展历史 大语言模型的发展历史可以追溯到早期的语言模型…

SpringBoot_第十章(日志)

目录 1&#xff1a;SpringBoot日志 2&#xff1a;项目启动日志验证 3&#xff1a;springboot日志级别 4&#xff1a;日志输出和级别控制 5&#xff1a;LogBack外部日志文件输出 6&#xff1a;自定义日志外部输出 6.1&#xff1a;logBack外部日志输出 6.2&#xff1a;log…