微服务 Spring Cloud 7,Nacos配置中心的Pull原理,附源码
目录
- 一、本地配置
- 二、配置中心
- 1、以Nacos为例:
- 2、Pull模式
- 3、也可以通过Nacos实现注册中心
- 三、配置中心提供了哪些功能
- 四、如何操作配置中心
- 1、配置注册
- 2、配置反注册
- 3、配置查看
- 4、配置变更订阅
- 五、主流的微服务注册中心有哪些,如何选择?
- 1、在选择微服务注册中心时,可以考虑以下因素:
- 2、主流注册中心
- (1)Eureka
- (2)Consul
- (3)Zookeeper
- (4)Nacos
- 3、如何选择?
- 微服务 Spring Cloud系列
大家好,我是哪吒。
在单体服务时代,关于配置信息,管理一套配置文件即可。
而拆分成微服务之后,每一个系统都会有自己的配置,并且都各不相同,有些配置还需要动态改变,以达到动态降级、切流量、扩缩容等目的。
一、本地配置
在Spring Boot开发中,可以把配置项放到config文件中,把配置当代码使用。比如:
public class AppConfig {public static final String static_SUCCESS_CODE = "0000";public static final String static_ERROR_CODE = "0001";
}
也可以通过@Value加载yaml配置文件中的配置。
@Component
public class HttpConfig {// 核心线程数public static String config_CORE_POOL_SIZE;@Value("${async.corePoolSize}")public void setSaveUrl(String corePoolSize) {HttpConfig.config_CORE_POOL_SIZE = corePoolSize;}
}
无论是将配置定义在代码中,还是将配置写在yaml配置文件中,都相当于把配置存在应用程序的本地。
如果想修改配置,就需要将在Linux服务器中部署的程序停止,然后手动修改其配置,再进行重启。
如果修改的配置项较多,这也是一项容易出错,而且繁琐的事情,长期运维的小伙伴应该深有体会。
当时,我就在想,作为世界上使用人数最多的语言,更新一个配置,需要这么复杂吗?
答案肯定不是的。
二、配置中心
配置中心(Configuration Center)通常用于集中管理应用程序的配置信息。这些配置信息可以包括数据库连接信息、外部服务地址、日志级别、超时设置等。配置中心可以提高应用部署的灵活性和可维护性。
程序启动时,可以自动从配置中心拉取所需要的配置项,配置中心中配置有所改变时,同样可以自动从配置中心拉取最新的配置信息,服务不需要重新发布。
1、以Nacos为例:
- 配置中心的信息一般都是放在bootstrap.yml 中;
- 初始化的时候,Bootstrap Context负责从外部源加载配置属性并解析配置;
- Bootstrap属性有高优先级,默认情况下,它们不会被本地配置覆盖;
- 然后再读取application.yml中的配置,进行配置合并,完成项目的启动。
项目的核心配置,需要热更新的配置才有放到nacos管理的必要。基本不会变更的一些配置还是保存在微服务本地比较好。
2、Pull模式
Nacos采用的是Pull模式获取服务端数据,客户端采用长轮询的方式定时的发起Pull请求,去检查服务端配置信息是否发生了变化。
- 客户端发起长轮询请求,监听变更的dataId+group;
- 服务端收到客户端的请求,这时会挂起客户端的请求;
- 如果在服务端设计的29.5s之内都没有发生变更,触发自动检查机制,此时不管是否有变化,服务端都会返回响应到客户端
- 如果在29.5s之内配置项发生了变更,则会触发一个事件机制,将变更的数据推送的客户端。
3、也可以通过Nacos实现注册中心
这种是最简单的Nacos注册中心,有若干个服务,都注册到Nacos注册中心,调用之前,先到Nacos获取对应接口,然后进行实际的调用。
服务1和服务2和Nacos之间维护一个心跳关系,每5秒跳一次,频率不能太快或者太慢,否者会嗝屁的。
如果Nacos在5秒内没有收到心跳,则表示服务挂了,Nacos会下线此服务。
对于超过15秒没有收到客户端心跳的服务实例,会将它的healthy属性置为false,客户端无法调用healthy为false的服务。
如果超过30秒没有收到心跳,Nacos会直接将此服务剔除。
也可以通过服务端主动注销的方式,停止注册。
服务1调用服务2时,服务1会通过定时任务到Nacos中获取在线的服务,保证所调用的服务一直都是健康在线的状态。
获取到之后,用缓存将其保存起来,然后通过负载均衡器调用服务2,此时,将不再使用服务端的负载均衡Nginx了。
三、配置中心提供了哪些功能
- 配置项管理:支持添加、发布、修改配置项以及配置项的分组,可以实现版本管理,支持热发布、灰度发布、环境隔离,提供API接口与可视化操作页面。
- 权限控制:配置项访问控制,读权限和写权限。
- 操作审计:支持记录用户的操作行为。
- 配置变更:当有新的配置项或是现有的配置项发生变动时,配置中心能够进行实时的监控并做出相应的处理。
- 配置推送:通过订阅/发布的模式,将配置信息推送给各个服务的消费者。
- 历史版本管理:保存所有的配置历史版本,并提供查询和对比的功能,可以轻松的回滚到任何一个版本。
- 灰度发布:通过配置中心可以实现在部分环境中先发布新的配置项,观察一段时间没有问题后再推送给其他所有的环境。
- 配置变更审计:记录每次配置的修改记录,方便追踪和管理。
这些功能可以帮助降低分布式系统中管理配置信息的成本,降低因错误的配置信息变更带来可用性下降甚至发生故障的风险。
四、如何操作配置中心
1、配置注册
配置中心的配置注册通常包括以下步骤:
- 服务提供者在启动时,将自己的配置信息注册到配置中心。这些信息可能包括服务的IP地址、端口号、数据库连接信息等。
- 配置中心接收并存储这些配置信息。一般来说,配置中心会提供一个统一的接口或者界面,让服务提供者能够方便地进行注册。
- 服务消费者在需要使用某个服务时,会从配置中心获取相应的配置信息。这样,即使服务提供者的地址等信息发生变化,服务消费者也能通过配置中心获取到最新的配置信息,而无需手动修改。
通过这种方式,配置中心实现了配置的统一管理和动态更新。服务提供者和消费者都可以通过配置中心来进行配置的注册和获取,大大提高了配置的灵活性和便利性。同时,也减少了因为手动配置错误而导致的问题,提高了系统的稳定性和可用性。
要通过Java代码实现配置注册到配置中心,你可以遵循以下步骤。这里继续提供一个通用的示例代码,以展示基本的流程和步骤。请注意,实际的代码可能会因所使用的具体配置中心而有所不同。
import com.configcenter.sdk.ConfigCenterClient;
import com.configcenter.sdk.exception.ConfigCenterException;
import com.configcenter.sdk.model.Configuration; public class ConfigurationRegistration { public static void main(String[] args) { // 配置中心的服务器URL和认证令牌 String serverUrl = "configcenter_server_url"; String authToken = "your_auth_token"; // 创建配置对象 Configuration configuration = new Configuration(); configuration.setId("your_configuration_id"); configuration.setKey("your_configuration_key"); configuration.setValue("your_configuration_value"); // 可选:设置其他配置项属性,如描述、标签等 try { // 初始化配置中心的客户端 ConfigCenterClient client = ConfigCenterClient.init(serverUrl, authToken); // 调用配置中心的注册API boolean success = client.registerConfiguration(configuration); if (success) { System.out.println("配置注册成功"); } else { System.out.println("配置注册失败"); } } catch (ConfigCenterException e) { System.out.println("配置注册出现异常: " + e.getMessage()); e.printStackTrace(); } }
}
在这个示例中:
- 我们首先创建了一个Configuration对象,设置了配置项的ID、键(key)和值(value)。你可以根据需要设置其他属性,如描述、标签等;
- 然后,我们初始化配置中心的客户端,并调用client.registerConfiguration()方法来执行配置注册操作,传入创建好的Configuration对象。
- 该方法将返回一个布尔值,表示注册是否成功,我们根据返回结果打印相应的消息;
- 如果发生异常,我们进行异常处理并打印异常信息。
2、配置反注册
配置中心的配置反注册是指从配置中心中移除或注销某个配置项的过程。当某个服务或应用不再需要使用某个配置项时,可以进行配置反注册操作。这个操作通常通过配置中心提供的接口来完成,它会将指定的配置项从配置中心中删除或标记为注销状态。
配置反注册可以是手动触发的,也可以是自动触发的。在手动触发方式下,管理员或开发者可以通过调用配置中心提供的反注册接口,指定需要反注册的配置项。而自动触发方式下,通常会在服务或应用停止时,自动触发配置反注册操作。
配置反注册是配置中心的一个重要功能,它可以帮助管理员或开发者更好地管理配置项的生命周期,确保配置中心中的数据与实际应用需求保持一致。同时,通过反注册不再需要的配置项,也可以减少配置中心的存储空间和资源消耗。
要通过Java代码实现配置反注册,你需要使用配置中心提供的Java SDK或API。以下是一个示例代码,展示了如何使用Java来实现配置反注册。
import com.configcenter.sdk.ConfigCenterClient;
import com.configcenter.sdk.exception.ConfigCenterException; public class ConfigurationDeregistration { public static void main(String[] args) { // 配置中心的服务器URL和认证令牌 String serverUrl = "configcenter_server_url"; String authToken = "your_auth_token"; // 初始化配置中心的客户端 ConfigCenterClient client = ConfigCenterClient.init(serverUrl, authToken); // 配置项的ID String configurationId = "your_configuration_id"; try { // 调用配置中心的反注册API boolean success = client.deregisterConfiguration(configurationId); if (success) { System.out.println("配置反注册成功"); } else { System.out.println("配置反注册失败"); } } catch (ConfigCenterException e) { System.out.println("配置反注册出现异常: " + e.getMessage()); e.printStackTrace(); } }
}
在这个示例中:
- 我们首先通过ConfigCenterClient.init()初始化配置中心的客户端,传入服务器URL和认证令牌;
- 然后,我们调用client.deregisterConfiguration()方法来执行配置反注册操作,传入配置项的ID;
- 该方法将返回一个布尔值,指示反注册是否成功;
- 根据返回结果,我们打印相应的消息;
- 如果发生异常,我们捕获并打印异常信息。
3、配置查看
通过配置中心的用户界面和API接口,你可以方便地查看和管理配置项。
import com.configcenter.sdk.ConfigCenterClient;
import com.configcenter.sdk.exception.ConfigCenterException;
import com.configcenter.sdk.model.Configuration; public class ConfigurationViewer { public static void main(String[] args) { // 配置中心的服务器URL和认证令牌 String serverUrl = "configcenter_server_url"; String authToken = "your_auth_token"; // 配置项的ID或键(key) String configurationId = "your_configuration_id"; // 或者使用配置项的键(key)来获取配置项,根据配置中心API的要求而定 // String configurationKey = "your_configuration_key"; try { // 初始化配置中心的客户端 ConfigCenterClient client = ConfigCenterClient.init(serverUrl, authToken); // 调用配置中心的API接口获取配置项 Configuration configuration = client.getConfiguration(configurationId); // 或者使用配置项的键(key)来获取: // Configuration configuration = client.getConfigurationByKey(configurationKey); // 输出配置项的信息 if (configuration != null) { System.out.println("配置项ID: " + configuration.getId()); System.out.println("配置项键(key): " + configuration.getKey()); System.out.println("配置项值(value): " + configuration.getValue()); // 输出其他配置项属性,如描述、标签等 } else { System.out.println("未找到配置项"); } } catch (ConfigCenterException e) { System.out.println("查看配置项出现异常: " + e.getMessage()); e.printStackTrace(); } }
}
在上面的示例代码中:
- 我们首先初始化配置中心的客户端;
- 然后调用相应的API接口来获取配置项;
- 在获取到配置项后,我们可以输出配置项的各种属性,如ID、键(key)、值(value)等;
- 如果发生异常,我们进行异常处理并打印相应的异常信息。
4、配置变更订阅
配置中心通常支持配置变更订阅功能,允许应用程序或其他服务订阅配置项的变更通知。当配置项发生变化时,配置中心会向订阅者发送通知,以便订阅者能够及时获取最新的配置项。
要通过Java代码实现配置变更订阅,你可以按照以下步骤进行操作:
- 首先,确保你已经初始化了配置中心的客户端,如上述示例代码所示。
- 创建一个订阅者(listener)类,实现配置中心提供的订阅接口。这个类将负责处理配置项的变更通知。
- 在订阅者类中,实现接口中定义的方法,以处理配置项的变更事件。该方法通常会在配置项发生变化时被调用,并且会接收包含变更信息的参数。
- 在你的应用程序或服务中,创建一个订阅请求(subscription request)对象,指定你希望订阅的配置项或配置项的过滤条件。
- 使用配置中心的客户端对象,调用订阅方法,将订阅请求对象和订阅者对象作为参数传递给该方法。这将向配置中心注册你的订阅请求,并指定订阅者类来处理变更通知。
- 一旦注册成功,当配置项发生变更时,配置中心将调用订阅者类中的方法,将变更信息传递给订阅者。你可以在这个方法中编写逻辑来处理配置项的变更,如更新本地缓存、重新加载配置等。
下面是一个简单的示例代码,展示如何实现配置变更订阅:
import com.configcenter.sdk.ConfigCenterClient;
import com.configcenter.sdk.exception.ConfigCenterException;
import com.configcenter.sdk.listener.ConfigurationChangeListener;
import com.configcenter.sdk.model.Configuration; public class ConfigurationSubscriber { public static void main(String[] args) { // 初始化配置中心的客户端(省略代码) // 创建订阅者类 ConfigurationChangeListener listener = new ConfigurationChangeListener() { @Override public void onConfigurationChanged(Configuration configuration) { // 处理配置项变更事件 System.out.println("配置项发生变化: " + configuration.getKey() + " = " + configuration.getValue()); // 在这里可以更新本地缓存、重新加载配置等 } }; try { // 创建订阅请求对象(根据配置中心API的要求而定) // 指定你希望订阅的配置项过滤条件,如配置项的键(key)或其他属性 // 调用配置中心的订阅方法 ConfigCenterClient client = ConfigCenterClient.init(serverUrl, authToken); client.subscribeToConfigurationChanges(filter, listener); } catch (ConfigCenterException e) { System.out.println("配置变更订阅出现异常: " + e.getMessage()); e.printStackTrace(); } }
}
五、主流的微服务注册中心有哪些,如何选择?
1、在选择微服务注册中心时,可以考虑以下因素:
- 功能和特性:不同的注册中心可能具有不同的功能和特性,需要根据自己的需求来选择。例如,一些注册中心可能更侧重于服务发现,而另一些可能提供更全面的配置管理功能。
- 性能和稳定性:注册中心作为微服务架构的核心组件,其性能和稳定性至关重要。需要对候选的注册中心进行性能测试和稳定性评估,确保它们能够满足你的业务需求。
- 易用性和开发体验:注册中心的易用性和开发体验也是选择的重要因素。选择一个提供良好开发文档、客户端库和工具的注册中心,可以使开发过程更加顺畅高效。
- 社区支持和生态系统:一个活跃和健康的社区可以为注册中心提供持续的支持和改进。同时,一个丰富的生态系统可以提供更多的集成选项和解决方案。因此,需要评估候选注册中心的社区活跃度和生态系统成熟度。
- 安全性和合规性:安全性和合规性对于任何系统都至关重要。需要确保所选的注册中心能够提供足够的安全保障,并满足你的合规性要求。
最终,选择微服务注册中心是一个权衡的过程,需要根据自己的实际需求、技术栈、团队熟悉度等因素进行综合考虑。
2、主流注册中心
在Eureka、Consul、Zookeeper和Nacos这几个微服务注册中心中,选择最适合的一个取决于你的具体需求和环境。
(1)Eureka
- 是Netflix开发的服务注册中心,与Spring Cloud集成良好。
- 保证了高可用性和最终一致性,服务注册相对较快。
- 在数据不一致时,每个Eureka节点仍能正常对外提供服务,保证了可用性。
(2)Consul
- 使用Go语言编写,具有较好的跨平台性。
- 提供了丰富的功能和强大的一致性保证。
- 支持多数据中心和分布式部署,适合大规模环境。
(3)Zookeeper
- 最初是一个分布式协调服务,后来被用于服务注册和发现。
- 提供了强一致性和高可用性,但相对较复杂,需要自行实现一些服务发现功能。
(4)Nacos
- 是阿里巴巴开源的项目,支持基于DNS和基于RPC的服务发现。
- 除了服务注册和发现,还支持动态配置服务。
- 在Spring Cloud中使用较为简单,只需简单的配置即可完成服务的注册和发现。
3、如何选择?
- 如果你使用Spring Cloud作为微服务框架,Eureka可能是一个自然的选择,因为它与Spring Cloud集成良好。
- 如果你需要强大的跨平台支持和一致性保证,Consul是一个不错的选择。
- 如果你已经在使用Zookeeper或其他Apache项目,并且希望在同一生态系统中解决服务注册和发现问题,那么Zookeeper可能适合你。
- 如果你在寻找一个简单且与阿里巴巴技术栈集成的解决方案,Nacos是一个值得考虑的选项。
最终的选择应基于你的技术需求、团队熟悉度和业务场景。
微服务 Spring Cloud系列
微服务 Spring Cloud 1,服务如何拆分?使用微服务的注意事项?
微服务 Spring Cloud 2,一文讲透微服务核心架构(注册中心、服务通信、服务监控、服务追踪、服务治理)
微服务 Spring Cloud 3,如何对微服务进行有效的监控?
微服务 Spring Cloud 4,分布式系统如何进行数据分区
微服务 Spring Cloud 5,一图说透Spring Cloud微服务架构
微服务 Spring Cloud 6,用了这么多年Docker容器,殊不知你还有这么多弯弯绕
🏆哪吒多年工作总结:Java学习路线总结,搬砖工逆袭Java架构师。
华为OD机试 2023B卷题库疯狂收录中,刷题点这里
刷的越多,抽中的概率越大,每一题都有详细的答题思路、详细的代码注释、样例测试,发现新题目,随时更新,全天CSDN在线答疑。
相关文章:

微服务 Spring Cloud 7,Nacos配置中心的Pull原理,附源码
目录 一、本地配置二、配置中心1、以Nacos为例:2、Pull模式3、也可以通过Nacos实现注册中心 三、配置中心提供了哪些功能四、如何操作配置中心1、配置注册2、配置反注册3、配置查看4、配置变更订阅 五、主流的微服务注册中心有哪些,如何选择?…...
c#Nettonsoft.net库常用的方法json序列化反序列化
Newtonsoft.Json 是一个流行的 JSON 操作库,用于在 .NET 应用程序中序列化、反序列化和操作 JSON 数据。下面是 Newtonsoft.Json 常用的一些方法: 序列化对象为 JSON 字符串: string json JsonConvert.SerializeObject(obj);var obj new {…...

力扣刷题-二叉树-二叉树的高度与深度
二叉树最大深度 给定一个二叉树 root ,返回其最大深度。 二叉树的 最大深度 是指从根节点到最远叶子节点的最长路径上的节点数。 示例 1: 输入:root [3,9,20,null,null,15,7] 输出:3 递归法 本题可以使用前序(中左…...
Vue3新增加的css语法糖
一、deep <template><div class""><el-input /> </div> </template> <style scoped> /* 样式穿透 */ :deep input {background: red; } </style> 二、slotted 子组件修改插槽里面的样式 <template><div clas…...

Windows安装Vmware 虚拟机
目录 一、Vmware 虚拟机介绍 二、Vmware 虚拟机的三种网络模式 2.1桥接模式 2.2仅主机模式 2.3NAT 网络地址转换模式 三、Vmware 虚拟机的安装 一、Vmware 虚拟机介绍 VMware Workstation Pro 是一款可以在个人电脑的操作系统上创建一个完全与主机操作系统隔离的 虚拟机&…...
uniapp地图手动控制地图scale
前言 首次使用uniapp开发地图过程中,发现uniapp地图居然没有提供手动控制地图scale的方法,这个也着实没有想到,查了半天资料,也终于找到一个方法能够比较好的控制scale,做个记录。 代码 要定义一个地图mapÿ…...

Kotlin学习之函数
原文链接 Understanding Kotlin Functions 函数对于编程语言来说是极其重要的一个组成部分,函数可以视为是程序的执行,是真正活的代码,为啥呢?因为运行的时候你必须要执行一个函数,一般从主函数入口,开始一…...

若依启动步骤
1.创建数据库 2.启动redis 3.改后端的数据库连接配置 4.配置redis redis的地址:cmd中ipconfig命令查看 6.启动后端:如下 7.启动前端ruoyi-ui中 先运行npm install,再npm run dev。项目就启动成功了。 用户名:admin 密码&#x…...

qt-C++笔记之两个窗口ui的交互
qt-C笔记之两个窗口ui的交互 code review! 文章目录 qt-C笔记之两个窗口ui的交互0.运行1.文件结构2.先创建widget项目,搞一个窗口ui出来3.项目添加第二个widget窗口出来4.补充代码4.1.qt_widget_interaction.pro4.2.main.cpp4.3.widget.h4.4.widget.cpp4.5.second…...

Redis-核心数据结构
五种数据结构 String结构 String结构应用场景 Hash结构 Hash结构应用场景 List结构 List结构应用场景 Set结构 Set结构应用场景 ZSet有序结构 ZSet有序结构应用场景...

设计模式—结构型模式之外观模式(门面模式)
设计模式—结构型模式之外观模式(门面模式) 外观(Facade)模式又叫作门面模式,是一种通过为多个复杂的子系统提供一个一致的接口,而使这些子系统更加容易被访问的模式。 例子 我们的电脑会有很多 组件&am…...
CentOS Stream 9-使用 systemd 管理自己程序时自定义日志路径
systemd 文件 [rootnode1 ~]# cat /etc/systemd/system/spms-wvp.service [Unit] DescriptionWVP service [Service] # 关键配置部分,注意这里的 spms-wvp ,后面需要用 SyslogIdentifierspms-wvp StandardOutputsyslog StandardErrorsyslog Typesimple Environment…...

动态页面调研及设计方案
文章目录 vue2 动态表单、动态页面调研一、form-generator二、ng-form-element三、Variant Form四、form-create vue2 动态表单、动态页面调研 一、form-generator 预览:https://mrhj.gitee.io/form-generator/#/ Vue2 Element UI支持拖拽生成表单不支持其他组件…...

鸿蒙4.0开发笔记之DevEco Studio之配置代码片段快速生成(三)
一、作用 配置代码片段可以让我们在Deveco Studio中进行开发时快速调取常用的代码块、字符串或者某段具有特殊含义的文字。其实现方式类似于调用定义好变量,然而这个变量是存在于Deveco Studio中的,并不会占用项目的资源。 二、配置代码段的方法 1、打…...

HarmonyOS真机调试报错:INSTALL_PARSE_FAILED_USESDK_ERROR处理
文章目录 1、 新建应用时选择与自己真机匹配的sdk版本2、 根据报错提示连接打开处理方案3、查询真机版本对应的**compileSdkVersion** 和 **compatibleSdkVersion** 提示3.1版本之后和3.1版本之前的不同命令(此处为3.0版本)4、根据查询修改参数5、连接成…...
webSocket基于面向对象二次封装
今天不睡,熬夜赶了个WebSocket 二次封装,也对这几天文章摸鱼感到抱歉,所以我出了一个注释非常非常全的代码 思路如下 首先,需要通过调用connect方法来建立WebSocket连接。当连接成功时,会调用我提供的回调函数,并将连接成功的消息帧作为参数…...

【Web】PHP反序列化的一些trick
目录 ①__wakeup绕过 ②加号绕过正则匹配 ③引用绕过相等 ④16进制绕过关键词过滤 ⑤Exception绕过 ⑥字符串逃逸 要中期考试乐(悲) ①__wakeup绕过 反序列化字符串中表示属性数量的值 大于 大括号内实际属性的数量时,wakeup方法会被绕过 (php5-p…...

【测试功能篇 01】Jmeter 压测接口最大并发量、吞吐量、TPS
压力测试,我们针对比较关键的接口,可以进行相应的压力测试,主要还是测试看看接口能抗住多少的请求数,TPS稳定在多少,也就是吞吐量多少 安装 Jmeter的安装很简单,官网下载地址 http://jmeter.apache.org/ &…...

代码随想录算法训练营第四十九天| 123.买卖股票的最佳时机III 188.买卖股票的最佳时机IV
文档讲解:代码随想录 视频讲解:代码随想录B站账号 状态:看了视频题解和文章解析后做出来了 123.买卖股票的最佳时机III class Solution:def maxProfit(self, prices: List[int]) -> int:if len(prices) 0:return 0dp [[0] * 5 for _ in…...

11.20 知识总结(choices参数、MVC和MTV的模式、Django与Ajax技术)
一、 choices参数的使用 1.1 作用 针对某个可以列举完全的可能性字段,我们应该如何存储 .只要某个字段的可能性是可以列举完全的,那么一般情况下都会采用choices参数 1.2 应用场景 应用场景: 学历: 小学 初中 高中 本科 硕士…...

深度学习二维码识别 计算机竞赛
文章目录 0 前言2 二维码基础概念2.1 二维码介绍2.2 QRCode2.3 QRCode 特点 3 机器视觉二维码识别技术3.1 二维码的识别流程3.2 二维码定位3.3 常用的扫描方法 4 深度学习二维码识别4.1 部分关键代码 5 测试结果6 最后 0 前言 🔥 优质竞赛项目系列,今天…...
C#关于TimeSpan结构的使用和获取两个时间差
C#中的TimeSpan结构可以获取两个时间的时间差。 它主要具有以下属性和方法: 属性: Days:获取时间间隔的天数部分。Hours:获取时间间隔的小时数部分(不包括整天的小时数)。Minutes:获取时间间…...

Git分支管理
愿所有美好如期而遇 目录 理解分支 创建分支 切换分支 合并分支 删除分支 合并冲突 分支管理策略 理解分支 每次提交master都会前进一步,随着不断提交,master分支的线越来越长,而HEAD指向哪条分支就是当前工作的分支。 master分支是我…...

《视觉SLAM十四讲》-- 建图
11 建图 11.1 概述 (1)地图的几类用处: 定位:导航:机器人在地图中进行路径规划;避障重建交互:人与地图之间的互动 (2)几类地图 稀疏地图稠密地图语义地图 11.2 单目…...

智能配电箱柜管理系统
智能配电箱柜管理系统是一个综合性的管理系统,专门设计用于监控和控制智能配电箱和柜的运行。这个系统集成了先进的技术和智能化功能,以确保配电系统的正常运行并提高其效率。依托电易云-智慧电力物联网,以下是智能配电箱柜管理系统的主要特点…...

聊聊近些年 CPU 在微架构、IO 速率上的演进过程
大家好,我是飞哥! 在上一篇《深入了解 CPU 的型号、代际架构与微架构》 中我们介绍了我手头的一颗 Intel(R) Core(TM) i5 的型号规则,以及它的物理硬件的 Die 图结构。以及它对应的 Skylake 核的微架构实现。 不少同学开始问我其它型号的 CPU…...

PS学习笔记——移动工具
文章目录 介绍文档内移动文档间移动 介绍 移动工具:用于移动图层中的对象,并且同一图层中的所有对象都将一起移动 选中移动工具后,选项栏中会出现“显示变换控件”,勾选后即可看见图层中的对象周围出现边框,可以进行缩…...

信息中心网络提出的背景、研究现状及研究内容
信息中心网络什么时候提出的?未来发展前景?有什么著名实验室在做? 1、提出背景: 互联网产生于上世纪60年代: (1)网络设备数量呈指数性增长 截至2022年底全球范围内预计将有超过280亿台终端设…...

【计算机视觉】24-Object Detection
文章目录 24-Object Detection1. Introduction2. Methods2.1 Sliding Window2.2 R-CNN: Region-Based CNN2.3 Fast R-CNN2.4 Faster R-CNN: Learnable Region Proposals2.5 Results of objects detection 3. SummaryReference 24-Object Detection 1. Introduction Task Defin…...
【mac 解决eclipse意外退出】
打开eclipse时提示报错信息应用程序"Eclipse.app"无法打开(这里忘了截图就不上图了)。 点击 “好” 的按钮后会弹出发送报告的弹窗 终端输入:sudo codesign --force --deep --sign - /Applications/Eclipse.app/ 就可以解决了...