SpringBoot自动化原理
SpringBoot自动化原理
在了解SpringBoot之前我们先要了解SpringBoot的相关注解和流程
SpringBoot相关注解如图:
SpringBoot的启动流程如图:
1、在SpringBoot使用过程中,我们使用到某个模块的功能,为什么依赖场景有的要写版本号,有的不用写呢?
比如webmvc,junit,redis不需要,mybatis需要
我们的工程继承了SpringBoot的夫工程Spring-boot-starter(版本2.3.10.release)
这个工程提供了53个场景,每个场景都搭建好了环境,并进行了版本锁定(比如webmvc场景引入了需要spingmvc包和tomcat插件等,做好了适配)所以对于springboot中提供的场景,无需编写版本号
但是对于springboot中没有提供的场景,而是第三方定义的场景,就需要编写版本号
2、我们使用springboot之后,springboot做了什么,让我们省略了很多繁杂的配置
这就需要了解springboot的自动化配置原理了大致可以简单的描述为:
1)springboot启动的时候都会加载每个场景下的xx-starter的METAINF/spring.factories文件类似于java中的spi机制
2)这个文件下有自动装配类
3)自动装配类中有很多配置类
4)只要满足特定条件下的配置类会被spring加载到IOC
这一套流程为开发者省略了很多繁杂的配置,体现了springboot约定大于配置的思想
3、如果我们搞懂了springboot的自动化配置原理是不是可以自己定义一些场景了?
是的,而且我们开发的项目中也需要根据业务封装一些场景
但是学习springboot的自动化配置原理不是简单的事:
1)spi机制
2)各种注解,接口和类
【2】SpringBoot自动装配预览
SPI全程Service Provider Interface ,是java提供的一套用来被第三方实现或者扩展的API,它可以用来启用框架扩展和替换组件。说白了,java的spi机制就是将一些类信息写在约定的文件中,然后由特定的类加载器加载解析文件获取资源;
SPI使用场景
场景 | 说明 |
---|---|
数据库驱动 | 数据库驱动加载接口实现类的加载不同类型的数据库驱动 |
日志门面SLF4J接口实现类加载 | SLF4J加载不同提供商的日志实现类 |
Spring | Spring中大量使用了spi,比如对servlet3.0规范对ServletContainerInitializer的实现,自动类型转换Type Conversion SPI(Converter SPI、Formatter SPI)等 |
Dubbo | Dubbo中也大量使用spi的方式实现框架的扩展,不过对java提供的原生spi做了封装,允许用户扩展实现Filter接口 |
SpringBoot | 基于SPI思想实现自动装配 |
java SPI实际上是基于接口编程+策略模式+配置文件组合实现的动态加载机制;
SpringBoot高级场景依赖starter介绍
通过依赖能了解SpringBoot管理了那些starter
1.通过依赖spring-boot-dependencies搜索starter发现非常多的官方starter,并且已经帮助我们管理好了版本提供了53个场景依赖
2.项目中使用直接引入对应的starter即可,这个场景下所有的依赖就会自动导入到项目中,简化了繁琐的依赖。
3.引入starter不仅仅是帮助我们管理了依赖,还帮我们做了很多默认的配置信息,简化了大量的配置,使用更加的简单。
4.大多数场景启动器的底层依赖spring-boot-starter【为场景依赖提供spring的核心环境】
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId><version>2.3.10.RELEASE</version><scope>compile</scope>
</dependency>
1.为什么引入SpringBoot默认的场景依赖,无需书写版本号
因为父工程通过dependentManager标签进行了版本的锁定与声明;
2.再配置满足当前开发需要的前提,为什么建议使用默认的配置
1.基于约定优于配置思想,减少开发中的繁琐的配置
2.SpringBoot帮助我们解决了资源依赖间版本兼容和冲突等问题
02-SpringBoot2高级-自动化配置初体验
目的:以spring-boot-starter-web场景依赖中自动化配置原理为例讲解,能够理解web MVC自动化配置加入那些依赖,做了那些默认配置
SpringMvc配置流程
1、首先添加SpringMvc相关的依赖资源spring-webmvc.jar、jackson相关,servlet相关等;
2、定义springmvc.xml配置文件,进行如下的配置
1).扫描controller所在包;
2).配置annotation-driven支持mvc扩展功能
3).试图解析器
4).静态资源
5).拦截器
6).
【1.3】配置web.xml
1、初始化spring容器
2.初始化springmvc DispatcherServlet核心调度器
3.请求乱码过滤器
4.配置tomcat,部署项目
也就是说在我们开发业务代码前,就必须要准备好这些环境,否则业务功能无法实现。
web场景依赖原理分析
当我们基于springboot使用web场景依赖时,我们发现要搭建一个标准的mvc工程,只需要引入spring-boot-starter-web场景依赖即可,几乎无需做其他配置,在这个过程中SpringBoot为我们做了大量的自动化配置工作;
接下来我们就探索一下SpringBoot是如何帮助我们完成强大而又简单自动化配置的。
引入web开发场景启动器依赖:
<!--web开发的起步依赖 场景启动器依赖-->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId>
</dependency>
我们发现spring-boot-starter-web场景依赖帮我们做了很多事:
引入webmvc工程相关的依赖资源:
工程自动加载依赖资源
通过断点测试SpringIOC容器,我们发现SpringBoot几乎把MVC相关的所有资源自动加载到容器中了:
1)自动装配SpringMVC核心组件(包括核心3大组件和文件上传等组件)
引入SpringMVC全套组件;
自动装配好SpringMVC常用组件(三大组件,文件上传等)
2)自动配好web常见功能,如:字符编码问题,静态资源管理,错误页面处理组件等;
3)SpringBoot默认自动扫描启动类同级以及所有子目录下资源;
1.引导类所在包及其下面的所有子包里面的组件会被默认扫描,无需像以前开启注解扫描
2.如果想要改变扫描路径@SpringBootApplication(scanBasePackages="com.xx.xx")或者@ComponentScan指定扫描路径
4)基于约定优于配置思想自动配置Tomcat常规参数
端口号:8080
字符键:UTF-8
参考:org.springframework.boot.autoconfigure.web.ServerProperties配置类
核心源码分析
在spring-boot-autoconfigure.jar资源包下META-INF/spring.factories文件下配置:
以org.springframework.boot.autoconfigure.web.servlet.DispatcherServletAutoConfiguration类为例,通过翻阅源码:
@Configuration(proxyBeanMethods = false)//定义配置类
@Conditional(DefaultDispatcherServletCondition.class)//满足指定条件则装配
@ConditionalOnClass(ServletRegistration.class)//满足指定类存在则装配
@EnableConfigurationProperties(WebMvcProperties.class)//加载配置对象
protected static class DispatcherServletConfiguration {
//自动装配springMVC核心调度器
@Bean(name = DEFAULT_DISPATCHER_SERVLET_BEAN_NAME)
public DispatcherServlet dispatcherServlet(WebMvcProperties webMvcProperties) {DispatcherServlet dispatcherServlet = new DispatcherServlet();dispatcherServlet.setDispatchOptionsRequest(webMvcProperties.isDispatchOptionsRequest());dispatcherServlet.setDispatchTraceRequest(webMvcProperties.isDispatchTraceRequest());dispatcherServlet.setThrowExceptionIfNoHandlerFound(webMvcProperties.isThrowExceptionIfNoHandlerFound());dispatcherServlet.setPublishEvents(webMvcProperties.isPublishRequestHandledEvents());dispatcherServlet.setEnableLoggingRequestDetails(webMvcProperties.isLogRequestDetails());return dispatcherServlet;
}
//.....
}
SpringBoot引入web场景依赖后,有什么好处
1.大量依赖资源自动装配,避免繁杂的XML配置;
2.可以使开发人员的中心聚焦与=于业务开发,提高开发效率;
SpringBoot2高级-底层原理-@Configuration配置注解
掌握@Configuration注解的作用及新特性
@Configuration注解使用
注解的作用是替代原始springXML配置文件功能
思考:
配置类中被@Bean修饰的方法被配置类bean对象多次调用返回的bean是否是同一个bean?
演示:
package com.xxx.config;import com.xxx.pojo.User;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.Date;//proxyBeanMethods = false:方法不会被代理 LITE模式 【多例模式】
@Configuration(proxyBeanMethods = false)
public class MyConfig {@Bean//方法默认被代理 FULL,实现单例模式public User myUser(){User user = new User().setId(1l).setBirthday(new Date()).setUserName("张三");return user;}
}
2)在引导类编写代码测试:
package com.xx;
import com.xx.config.MyConfig;
import com.xx.pojo.User;
import org.apache.tomcat.util.net.jsse.JSSEUtil;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;import java.util.Map;/*** 编写引动类/启动类* @SpringBootApplication注解定义当前类为springboot的引导类*/
@SpringBootApplication
public class SpringConfigurationApp {/*** main方法是springboot* 启动的入口* @param args*/public static void main(String[] args) {//获取ioc容器ConfigurableApplicationContext ctx = SpringApplication.run(SpringConfigurationApp.class, args);//key:bean名称 value:bean对象// 发现MyConfig被cglib动态代理了:从ioc容器检查指定的bena是否存在,如果存在,直接返回ioc容器中的bean FULLMap<String, MyConfig> beanInfo = ctx.getBeansOfType(MyConfig.class);System.out.println(beanInfo);Map<String, User> userInfo = ctx.getBeansOfType(User.class);System.out.println(userInfo);//获取myconfig对象MyConfig myConfig = ctx.getBean(MyConfig.class);User user1 = ctx.getBean(User.class);User user2 = myConfig.myUser();System.out.println(user1==user2);}
}
【2】proxyBeanMethods属性说明
@Configuration注解下proxyBeanMethods属性表示代理bean的方法属性【since spring5.2】
功能:
proxyBeanMethods=true :Full模式(默认),保证每个@Bean方法被调用多少次返回的组件都是单实例的;
proxyBeanMethods=false:Lite模式,每个@Bean方法被调用多少次返回的组件都是新创建的
演示:
1、默认proxyBeanMethods=true,springBoot会检查这个组件是否在容器中有,有则直接引用
默认proxyBeanMethods=true,springBoot会检查这个组件是否在容器中有,有则直接引用
User user3=myConfig1.getUser();
System.out.println(user1==user3);//true
2.修改proxyBeanMethods=false,则每调用一次Spring就会创建一个新的Bean对象
在执行结果则为false,证明两次获取的bean不是同一个bean
【3】小结
【1】在注解@Configuration修饰的配置类下,调用构建bean的方法时,如何实现单例或者多例模式?
# 通过proxyBeanMethods属性指定:
1. proxyBeanMethods=true :full模式,也就是单例模式,每次方法被调用时不会立即创建,会先从IOC容器检查是否有指定类型的bean,如果有,则直接返回,如果没有,调用方法创建;<br>
2. proxyBeanMethods=false:lite模式,也就是多例模式,每次方法被调用,直接创建对象;
【2】在初次构建bean对象时FULL模式与LITE模式哪个执行效率相对较高?
1. LITE模式,因为构建对象时无需从IOC容器检查对象是否存在,相对效率高一些;
2. 这也是自动化装配类选择使用LITE模式的核心原因所在(项目启动快)
04-springBoot2高级-底层原理@Import注解使用1
目的:
@Import注解学习是为接下来的源码阅读做准备的;
理解@Import注解的作用及四种使用方式;
作用:
使用@Import导入的类会被Spring加载到IOC容器中
@Import提供4中用法:
1.直接导入一个类,实例化后作为一个Bean被IOC容器管理
2.导入配置类
3.导入ImportSelector实现类。一般用于加载配置文件中的类
4.导入ImportBeanDefinitionRegistrar实现类
实现:
【1】导入Bean
package com.xxx.xxx;import com.xxx.xxx.pojo.User;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Import;import java.util.Map;@SpringBootApplication
@Import(User.class)
//会自动执行当前类的构造方法创建对象,存到IOC容器, bean名称为:类的全路径
public class SpringConfigurationApp {public static void main(String[] args) {ConfigurableApplicationContext applicationContext = SpringApplication.run(DataApplication.class, args);//获取bean的名称与对象对应的键值对对象Map<String, User> map = applicationContext.getBeansOfType(User.class);System.out.println(map);User user1 = applicationContext.getBean("com.itheima.sh.pojo.User", User.class);System.out.println(user1);}
}
【2】导入配置类
定义配置类:
package com.xxx.config;import com.xxx.pojo.User;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.Date;@Configuration
public class MyConfig {@Bean//方法默认被代理 FULL,实现单例模式public User myUser(){User user = new User().setId(1l).setBirthday(new Date()).setUserName("张三");return user;}
}
导入配置类:
package com.xxx;
import com.xxx.config.MyConfig;
import com.xxx.config.MyImportBeanDefinitionRegistrar;
import com.xxx.config.MyImportSelector;
import com.xxx.pojo.User;
import org.apache.tomcat.util.net.jsse.JSSEUtil;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Import;import java.util.Map;/*** 编写引动类/启动类* @SpringBootApplication注解定义当前类为springboot的引导类*/
@SpringBootApplication
//方式1:导入类最终实例化成bena为ioc容器维护 bean名称:类的全限定名称
//@Import(User.class)
//方式2:导入配置类 ,配置类下的@Configuration可以省略
@Import(MyConfig.class)
public class SpringConfigurationApp {public static void main(String[] args) {//获取ioc容器ConfigurableApplicationContext ctx = SpringApplication.run(SpringConfigurationApp.class, args);//@Import(User.class) bean名称:类的全限定名称Map<String, User> userBean = ctx.getBeansOfType(User.class);System.out.println(userBean);User user = ctx.getBean("com.itheima.pojo.User", User.class);System.out.println(user);}
}
05-SpringBoot2高级-底层原理-@Import注解使用2
目的:注解@Import注解使用另外两种使用方式
步骤:
1.导入ImportSelector实现类。一般用于加载配置文件中的类
2.导入ImportBeanDefinitionRegistrar实现类
实现:
【1】导入ImportSelector实现类
场景:一般用用于批量导入第三方资源bean
1、编写ImportSelector接口的实现类MyImportSelector
package com.xxxx.config;import org.springframework.context.annotation.ImportSelector;
import org.springframework.core.type.AnnotationMetadata;
import java.util.Set;public class MyImportSelector implements ImportSelector {/*** @Import注解打到哪个类下,那么类下的注解元数据信息通过AnnotationMetadata注入到selectImports方法下* 实现批量导入* @param annotationMetadata* @return*/@Overridepublic String[] selectImports(AnnotationMetadata annotationMetadata) {Set<String> sets = annotationMetadata.getAnnotationTypes();return new String[]{"com.itheima.pojo.User"};}
}
2、引导类导入
package com.xxx;
import com.xxx.config.MyConfig;
import com.xxx.config.MyImportBeanDefinitionRegistrar;
import com.xxx.config.MyImportSelector;
import com.xxx.pojo.User;
import org.apache.tomcat.util.net.jsse.JSSEUtil;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Import;import java.util.Map;/*** 编写引动类/启动类* @SpringBootApplication注解定义当前类为springboot的引导类*/
@SpringBootApplication
//方式1:导入类最终实例化成bena为ioc容器维护 bean名称:类的全限定名称
//@Import(User.class)
//方式2:导入配置类 ,配置类下的@Configuration可以省略
//@Import(MyConfig.class)
//方式3:实现批量导入组件
@Import(MyImportSelector.class)
public class SpringConfigurationApp {/*** main方法是springboot* 启动的入口* @param args*/public static void main(String[] args) {//获取ioc容器ConfigurableApplicationContext ctx = SpringApplication.run(SpringConfigurationApp.class, args);//@Import(User.class) bean名称:类的全限定名称Map<String, User> userBean = ctx.getBeansOfType(User.class);
// System.out.println(userBean);
// User user = ctx.getBean("com.itheima.pojo.User", User.class);
// System.out.println(user);}
}
【2】导入ImportBeanDefinitionRegistrar 接口实现类
1、编写 ImportBeanDefinitionRegistrar接口实现类:MyImportBeanDefinitionRegistrar
package com.xxx.config;import com.xxxx.pojo.User;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.context.annotation.ImportBeanDefinitionRegistrar;
import org.springframework.core.type.AnnotationMetadata;public class MyImportBeanDefinitionRegistrar implements ImportBeanDefinitionRegistrar {/**** @param importingClassMetadata @Import注解作用的类下的元数据信息封装* @param registry 注册bean信息的注册对象*/@Overridepublic void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {//1.创建bena的定义信息AbstractBeanDefinition userDefinition = BeanDefinitionBuilder.rootBeanDefinition(User.class).getBeanDefinition();/*** 参数1:bean的名称* 参数2:bean的定义对象*/registry.registerBeanDefinition("user",userDefinition);}
}
2、引导类测试
package com.xxx;
import com.xxxx.config.MyConfig;
import com.xxxx.config.MyImportBeanDefinitionRegistrar;
import com.xxxx.config.MyImportSelector;
import com.xxxx.pojo.User;
import org.apache.tomcat.util.net.jsse.JSSEUtil;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Import;import java.util.Map;/*** 编写引动类/启动类* @SpringBootApplication注解定义当前类为springboot的引导类*/
@SpringBootApplication
//方式1:导入类最终实例化成bena为ioc容器维护 bean名称:类的全限定名称
//@Import(User.class)
//方式2:导入配置类 ,配置类下的@Configuration可以省略
//@Import(MyConfig.class)
//方式3:实现批量导入
//@Import(MyImportSelector.class)
//方式4:通过ImportBeanDefinitionRegistrar实现类完成导入,也能完成bena的批量导入
@Import(MyImportBeanDefinitionRegistrar.class)
public class SpringConfigurationApp {public static void main(String[] args) {//获取ioc容器ConfigurableApplicationContext ctx = SpringApplication.run(SpringConfigurationApp.class, args);//@Import(User.class) bean名称:类的全限定名称
// Map<String, User> userBean = ctx.getBeansOfType(User.class);
// System.out.println(userBean);
// User user = ctx.getBean("com.itheima.pojo.User", User.class);
// System.out.println(user);//@Import(MyConfig.class)User user2 = ctx.getBean("user",User.class);System.out.println(user2);}
}
【3】小结
使用@Import注解的4种方式?
1. 直接导入Bean
2. 导入配置类★
3. 导入ImportSelector 实现类。一般用于加载配置文件中的类 ★★
4. 导入ImportBeanDefinitionRegistrar实现类
06-SpringBoot2高级-底层原理-@Conditional衍生条件装配
目的:理解@Conditional衍生条件装配的作用
作用:条件装配,满足Conditional指定的条件,则进行组件注入,初始化Bean对象到IOC容器
【1】SpringBoot常用条件注解
ConditionalOnClass:工程环境中必须存在指定的字节码文件才初始化Bean
ConditionalOnMissingBean:IOC容器中没有对应Bean才初始化Bean
ConditionalOnProperty:判断配置文件中是否有对应属性和值才初始化Bean
【2】代码演示
package com.itheima.config;import com.itheima.pojo.User;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;import java.util.Date;@Configuration
//【1】User类存在,那么当前的配置bean就会被加载到ioc容器下
//@ConditionalOnClass(name = {"com.itheima.pojo.User"})
//【2】与@ConditionalOnClass功能相反
//@ConditionalOnMissingClass(value = {"com.itheima.pojo.User"})
//【3】当指定类型的bean在ioc容器中不存在,那么生效
//@ConditionalOnMissingBean(type = {"com.itheima.pojo.User"})
//【4】属性:prefix指定配置文件前缀 name:指定后缀之后的key 如果存在则满足条件,注解作用的bean加载
//配合文件必须配置myredis.enable=true才能被创建
@ConditionalOnProperty(prefix = "myredis",name = "enable",havingValue = "true")
public class MyConfig {@Beanpublic User myUser(){User user = new User().setId(1l).setBirthday(new Date()).setUserName("张三");return user;}
}
测试:
package com.xxx;
import com.xxx.config.MyConfig;
import com.xxx.pojo.User;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;@SpringBootApplication
public class SpringConfigurationApp {public static void main(String[] args) {//获取ioc容器ConfigurableApplicationContext ctx = SpringApplication.run(SpringConfigurationApp.class, args);User bean = ctx.getBean(User.class);System.out.println(bean);}
}
注意:条件注解不仅可以添加到类上也可以作用在方法之上;
【3】小结
1Spring提供的条件注解有什么作用?
spring提供的@ConditionalOnxxx注解作用:满足条件当前类或者Bean才有效,按需导入;
2.Spring常用条件注解有哪些,各有什么作用?
1. @ConditionalOnClass:项目环境中存在指定的字节码文件才初始化Bean对象
2. @ConditionalOnMissingBean:IOC容器中没有指定的Bean对象才初始化注解作用的Bean
3. @ConditionalOnProperty:判断配置文件中是否有对应属性和值才初始化Bean
07-SpringBoot2高级-底层原理-@ConfigurationProperties配置绑定
回顾 @ConfigurationProperties配置绑定 存在的目的是:
获取配置属性或者是配置文件指定前缀的属性信息,并且初始化Bean对象到 IOC 容器。
由此我们可以想:将来的配置我们可以放在配置文件中,通过这个注解来读取并封装成对象,这样避免了配置属性需要逐个注入获取的问题;
08-SpringBoot2高级-自动化配置原理-@SpringBootApplication入口分析
目的:能够理解SpringBoot自动化配置流程中@SpringBootApplication是一个组合注解,及每一个注解的作用能够知道作用。
讲解:
1、SpringBoot是一个组合注解
2、@SpringBootConfiguration注解作用
- @SpringBootConfiguration是对@Configuration注解的包装,proxyBeanMethods 默认配置 true, full模式(单例Bean)
- 标识是一个配置类,所以 引导类也是配置类 ;
3、@ComponentScan注解作用 - 组件扫描,默认扫描的规则 引导类所在的包及其子包所有带Spring注解的类
问题:
1、在SpringBoot引导类中可以使用@Bean 注解可以吗?
可以,因为@SpringBootApplication注解中@SpringBootConfiguration注解对@Configuration做了层包装,本质也是一个配置注解
2、为什么启动类路径下的Controller、service类添加Spring bean注解后,不需要添加注解扫描,就可以被加载?
SpringBooot通过@ComponentScan默认加载主类路径及其子包路径;
09-SpringBoot2高级-自动化配置原理-@EnableAutoConfiguration自动配置注解
目的:理解@EnableAutoConfiguration自动化配置核心实现注解
讲解:
本章节我们将通过注解源码阐述SpringBoot加载【工程内部资源】和【第三方starter资源】的加载机制;
【1】@EnableAutoConfiguration浅析
通过查看源码,我们发现@EnableAutoConfiguration也是一个组合注解。
【2】@AutoConfigurationPackage注解作用
作用:利用Registrar给容器中导入一系列组件
点击 Registrar
进入到源码的 register
方法,添加 断点,测试
通过 debug 程序,我们发现@AutoConfigurationPackage注解底层会将SpringBoot启动类所在路径封装到BasePackage 类,并注册到IOC容器中,这样配合@ComponentScan注解完成加载启动类同级以及所有子目录下的资源被加载;
总之,@AutoConfigurationPackage核心作用是确定@ComponentScan注解扫描包的范围;
【3】@Import(AutoConfigurationImportSelector.class)注解作用
作用:是利用selectImports
方法中的 getAutoConfigurationEntry
方法给容器中批量导入相关组件;
调用流程分析:
- 调用
AutoConfigurationImportSelector
类中的selectImports
方法; selectImports
方法底层调用getAutoConfigurationEntry()
方法获取可自动装配的配置类信息集合;getAutoConfigurationEntry()
方法调用getCandidateConfigurations(annotationMetadata, attributes)
方法获取所有基于META-INF/spring.factories文件下的自动配置类的集合;【127个自动装配的信息】- 底层利用Spring工厂加载器调用
loadSpringFactories()
方法扫描当前系统中所有META-INF/spring.factories文件,并加载获取自动配置类信息;
默认扫描我们当前系统里面所有META-INF/spring.factories位置的文件
当然,spring-boot-autoconfigure-2.3.4.RELEASE.jar包里面也有META-INF/spring.factories
通过这个配置文件加载的自动配置:当前版本(2.3.10)是有127个默认的自动化配置
5.获取所有META-INF/spring.factories下的自动装配的配置类后,然后根据是否满足装配条件进行过滤:
configurations = removeDuplicates(configurations);
Set<String> exclusions = getExclusions(annotationMetadata, attributes);
checkExcludedClasses(configurations, exclusions);
configurations.removeAll(exclusions);
//根据本工程的配置,过滤不满足@ConditionlOnxxx
configurations = getConfigurationClassFilter().filter(configurations);
小结:
【1】SpringBoot默认自动加载的配置文件路径是哪里?
当前项目系统路径下的所有META-INF/spring.factories文件
【2】简述SpringBoot自动装配流程?
1. 通过@Import注解调用AutoConfigurationImportSelector类中的selectImports方法;
2. selectImports方法底层调用getAutoConfigurationEntry()方法获取可自动装配的配置类信息集合;
3. getAutoConfigurationEntry()方法调用getCandidateConfigurations(annotationMetadata, attributes)方法获取所有基于META-INF/spring.factories文件下的自动配置类的集合;
4. 底层利用Spring工厂加载器调用 loadSpringFactories()方法扫描当前系统中所有META-INF/spring.factories文件,并加载获取自动配置类信息;
5. 根据@Conditional条件过滤,获取最终自动装配类,最后被IOC容器加载;
10-SpringBoot2高级-自动化配置原理-条件装配过滤示例
目的:
- 能够理解所有的自动化配置虽然会全部加载,底层有大量的@ConditionalOnXXX,有很多自动配置类并不能完全开启。
- 如果配置生效了,则会加载默认的属性配置类,实现默认的对应场景的自动化配置
讲解:
1、以上通过META-INF/spring.factories
配置文件找到所有的自动化配置类,但 是不是全部的生效的呢?很显然是不可能全部都生效的。
2、以RedisAutoConfiguration
为例讲解, 进入到RedisAutoConfiguration
自动化配置类。
//定义当前注解作用类是配置类 proxyBeanMethods = false使用后lite模式,项目启动快
@Configuration(proxyBeanMethods = false)
//RedisOperations这个类存在,则满足加载条件 也就是说工程需要引入spring-data-redis-2.3.9.RELEASE.jar
@ConditionalOnClass(RedisOperations.class)
//开启配置属性类的加载,RedisProperties类被加载到IOC容器下
@EnableConfigurationProperties(RedisProperties.class)//配置属性bean通过构造器方式注入到工厂bean下
//导入满足条件的工厂配置类,sringboot推荐使用 Lettuce, 性能最好
@Import({ LettuceConnectionConfiguration.class, JedisConnectionConfiguration.class })
public class RedisAutoConfiguration {@Bean//如果IOC容器中不存在名称为redisTemplate的bean,那么该方法就满足条件//好处:为客户端充足的扩展,如果我们自定义了redisTempalte,那么springboot就不会自动装配@ConditionalOnMissingBean(name = "redisTemplate")public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory)throws UnknownHostException {RedisTemplate<Object, Object> template = new RedisTemplate<>();template.setConnectionFactory(redisConnectionFactory);return template;}//StringRedisTemplate仅操纵数据类型是string的场景@Bean@ConditionalOnMissingBeanpublic StringRedisTemplate stringRedisTemplate(RedisConnectionFactory redisConnectionFactory)throws UnknownHostException {StringRedisTemplate template = new StringRedisTemplate();template.setConnectionFactory(redisConnectionFactory);return template;}
}
3、RedisProperties
属性对象,用于加载默认的配置,如果配置文件配置了该属性,则配置文件就生效。
4、LettuceConnectionConfiguration
是当前版本默认使用的Redis的连接池(性能较好)
SpringBoot工程中没有引入的starter,是否能被加载到工程内?为什么?
自动装配配置类中只有满足conditional条件的配置类,才会被加载到IOC容器中;
11-SpringBoot2高级-自动化配置原理-总结
SpringBoot自动化配置流程总结:
- SpringBoot启动找到自动化配置包下
META-INF/spring.factories
内的EnableAutoConfiguration
配置列表; - 每个自动配置类按照条件进行生效,默认都会绑定配置文件指定的值;
- 生效的配置类就会给容器中装配很多组件;
- 只要容器中有这些组件,相当于这些功能就有了
总之SpringBoot加载所有META-INF/spring.factories文件下的自动装配类,然后通过条件过滤获取可被装配的配置类,然后配置类被spring加载到IOC容器下;
二、SpringBoot自定义starter (掌握)
12-SpringBoot2高级-自定义starter-步骤分析
**需求:**自定义heima-redis-spring-boot-starter场景启动依赖,并成功集成到新项目下;
**技术要求:**基于Spring环境使用Jedis和RedisTemplate构建redis场景依赖工程;
步骤:
【1】创建 wunian-redis-spring-boot-starter 工程模块,打包方式为jar,添加相关依赖;
依赖清单 | 说明 |
---|---|
spring-boot-starter | 为自定义redis场景依赖提供spring核心环境 |
spring-boot-configuration-processor | 辅助配置文件时提示说明 |
spring-data-redis | spring整合redis的中间包,提供RedisTemplate等核心API |
jedis | java底层连接redis服务的客户端技术 |
lombok | 方便配置属性类setter方法生成 |
【2】添加配置属性类;
作用:将工程中关于redis的配置信息封装到一个配置类下,方便获取配置参数;
【3】添加自动配置类;
作用:加入条件装配信息,动态构建操纵redis的RedisTemplate对象;
【4】在工程resources下定义META-INF/spring.factories 文件,让SpringBoot自动识别并加载;
操作:将自定义的配置类定义在该文件中,使得SpringBoot识别加载;
【5】在测试模块中引入自定义的 heima-redis-spring-boot-starter 依赖,测试;
13-SpringBoot2高级-自定义starter-实现
【1】构建starter工程
<parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.3.10.RELEASE</version><relativePath/> <!-- lookup parent from repository -->
</parent>
<properties><java.version>1.8</java.version><redis.version>2.3.9.RELEASE</redis.version>
</properties>
<packaging>jar</packaging>
<dependencies><!--为场景依赖提供spring的基础环境--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId></dependency><!--开发配置提醒--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-configuration-processor</artifactId><optional>true</optional></dependency><!--spring整合redis的整合包--><dependency><groupId>org.springframework.data</groupId><artifactId>spring-data-redis</artifactId><scope>compile</scope></dependency><!--引入jedis客户端依赖--><dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId></dependency><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></dependency>
</dependencies>
【2】添加配置属性类
package com.xxx.pros;import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;/*** 自动化默认属性配置类:读取配置文件下的数据映射配置对象*/
@Data
@ConfigurationProperties(prefix = "myredis.config")
public class MyRedisProps {//定义redis host主机地址private String host="localhost";//端口号private Integer port=6379;//定义数据库 0~15private Integer db=0;
}
【3】添加条件配置类
package com.xxx.redis;import com.xxx.pros.MyRedisProps;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;/*** 定义redis自动装配类*/
@Configuration(proxyBeanMethods = false)
//必须使用jedis,且必须引入spring-data-redis.jar,完成对redis的操作
@ConditionalOnClass(name = {"redis.clients.jedis.Jedis","org.springframework.data.redis.core.RedisOperations"})
@EnableConfigurationProperties(MyRedisProps.class)
public class MyRedisAutoConfiguration {private MyRedisProps myRedisProps;/*** 构造器注入MyRedisProps类型的bean* @param myRedisProps*/public MyRedisAutoConfiguration(MyRedisProps myRedisProps) {this.myRedisProps = myRedisProps;}@Bean//容器中不存在名称为redisTemplate的bean则创建@ConditionalOnMissingBean(name = "redisTemplate")public RedisTemplate redisTemplate(){//1.创建连接工程JedisConnectionFactory connectionFactory = new JedisConnectionFactory();connectionFactory.setHostName(myRedisProps.getHost());connectionFactory.setPort(myRedisProps.getPort());connectionFactory.setDatabase(myRedisProps.getDb());//1.创建RedisTemplate对象RedisTemplate<Object, Object> redisTemplate = new RedisTemplate<>();redisTemplate.setConnectionFactory(connectionFactory);//2.设置对象序列化支持redisTemplate.afterPropertiesSet();return redisTemplate;}
}
【4】定义spring.factories
在resources下定义META-INF/spring.factories 文件,并配置自动装配信息,让SpringBoot自动加载:
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
com.xxx.redis.MyRedisAutoConfiguration
【5】安装自定starter
maven安装到本地仓库,方便其它工程引用
14-SpringBoot2高级-自定义starter-集成到新项目
目的:验证自定义starter是否可以使用
实现:
【1】新建 boot_xxxedis
项目中引入依赖
<!--1、引入SpringBoot父工程-->
<parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.3.10.RELEASE</version>
</parent><dependencies><!--web 启动器 SpringBoot对web的支持--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId></dependency><dependency><groupId>com.itheima.sh</groupId><artifactId>heima-redis-spring-boot-starter</artifactId><version>1.0-SNAPSHOT</version></dependency></dependencies>
【2】定义yml配置
myredis:config:host: 127.0.0.1port: 6379db: 1
【2】测试
package com.xxx;import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.redis.core.RedisTemplate;@SpringBootTest
public class TestMyStarter {@Autowiredprivate RedisTemplate redisTemplate;@Testpublic void test1(){redisTemplate.opsForValue().set("name","lisi");Object name = redisTemplate.opsForValue().get("name");System.out.println(name);}
}
三、SpringBoot健康监控
15-SpringBoot2高级-监控-健康监控服务
目的:能够理解健康监控actuator
的作用
背景:
在一些大型的业务应用中,工程会根据业务模块做微服务拆分,后期每一个微服务在云上部署以后,都需要对其进行监控、追踪、审计、控制等操纵,这会给维护人员带来很大的运维压力。
SpringBoot对此就抽取了Actuator场景,使得我们每个微服务快速引用即可获得生产级别的应用监控、审计等功能。
实现:
1、被监控工程中引入Actuator依赖
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
2、启动项目,访问 http://localhost:80/actuator/**
3、暴露所有监控信息为HTTP
management:endpoints:enabled-by-default: true #暴露所有端点信息web:exposure:include: '*' #以web方式暴露endpoint:health:enabled: true # 开启健康检查详细信息show-details: always
访问 http://localhost:80/actuator
会发现内容多了,里面的地址分别都可以访问,记录的是对应的健康监测的信息。
16-SpringBoot2高级-监控-Admin可视化
目的:能够搭建 可视化监控平台
讲解:
【1】Admin可视化介绍
SpringBoot Admin 有两个角色,客户端(Client)和服务端(Server)。
Spring Boot Admin为注册的应用程序提供以下功能:
- 显示健康状况
- 显示详细信息,例如
- JVM和内存指标
- micrometer.io指标
- 数据源指标
- 缓存指标
- 显示内部信息
- 关注并下载日志文件
- 查看JVM系统和环境属性
- 查看Spring Boot配置属性
- 支持Spring Cloud的可发布/ env-和// refresh-endpoint
- 轻松的日志级别管理
- 与JMX-beans交互
- 查看线程转储
- 查看http-traces
- 查看审核事件
- 查看http端点
- 查看预定的任务
- 查看和删除活动会话(使用spring-session)
- 查看Flyway / Liquibase数据库迁移
- 下载heapdump
- 状态更改通知(通过电子邮件,Slack,Hipchat等)
- 状态更改的事件日志(非持久性)
快速入门:https://codecentric.github.io/spring-boot-admin/2.3.1/#getting-started
实现:
以下为创建服务端和客户端工程步骤:
【1】搭建Server端
1、创建 admin_server 模块,引入依赖
<parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.3.10.RELEASE</version><relativePath/> <!-- lookup parent from repository -->
</parent><dependencies><dependency><groupId>de.codecentric</groupId><artifactId>spring-boot-admin-starter-server</artifactId><version>2.3.1</version></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency>
</dependencies>
2、开启注解支持
package com.xxx.sh;import de.codecentric.boot.admin.server.config.EnableAdminServer;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
@EnableAdminServer
public class AdminApplication {public static void main(String[] args) {SpringApplication.run(AdminApplication.class, args);}
}
注意端口修改为:9999
【3】搭建Client端
1、在任意服务里面引入依赖
<dependency><groupId>de.codecentric</groupId><artifactId>spring-boot-admin-starter-client</artifactId><version>2.3.1</version>
</dependency>
2、配置文件
# 执行admin.server地址
spring: boot:admin:client:url: http://localhost:9999 # admin 服务地址instance:prefer-ip: true # 显示IPapplication:name: boot_data # 项目名称management:endpoints:enabled-by-default: true #暴露所有端点信息web:exposure:include: '*' #以web方式暴露endpoint:health:enabled: true # 开启健康检查详细信息show-details: always
【4】启动服务端和客户端测试
启动服务,访问admin Server http://localhost:9999/
四、SpringBoot项目部署
SpringBoot 项目开发完毕后,支持两种方式部署到服务器
- jar包部署
1. 将要部署的项目打成jar包1). 注意: 导入springboot打包插件
2. 丢到linux系统上1). 注意mx在连接linux的时候,如果连不上,查看services.msc中vm开头的服务有没都启动
3. 在linux上启动项目 1). java -jar xx.jar前端启动,界面不能关闭2). linux防火墙默认只开放22端口I. 安装软件的时候,开放了8080,3306,6379II. 要么开放9999,要么关闭防火墙systemctl stop firewalld3). 后端启动(启动时不在终端打印日志,在文件中打印,默认文件名 nohup.out)nohup java -jar xx.jar &
4. 在windows上用浏览器访问http://192.168.109.122:9999/5. linux命令1). pwd : print working directory 打印当前工作路径2). ps -ef | grep java : 查看当前系统中包含有java关键字的进程3). cat 文件 : 查看
war包部署
1. 将要部署的项目打成war包1). spring-boot-starter-web环境要排除tomcat.jar(运行起来用linux系统中的tomcat软件)2). 引入servlet的jar包,不然编译会报错3). 插件中声明打war包不需要web.xml,不然会报错4). 打包方式为war5). 修改启动类(继承SpringBootServletInitializer重写configure方法)
2. 丢到linux系统的tomcat/webapps目录下3. 启动tomcat,就会加载我们的项目1). bin目录 ./startup.sh2). 访问http://192.168.109.122:8080/war包名字/controller虚拟路径
17-SpringBoot2高级-服务部署-jar包部署
目的:能够使用Jar包方式部署SpringBoot项目
实现:
1、引入打包插件依赖
<build><!--声明jar包名称--><finalName>boot_data</finalName><plugins><plugin><groupId>org.springframework.boot</groupId><artifactId>spring-boot-maven-plugin</artifactId></plugin></plugins>
</build>
2、打包,复制出Jar使用,java -jar
运行程序
复制到任意Linux目录:
正常访问;
注意事项:
1.项目运行必须依赖 JDK 环境;
2. 注意linux的防火墙9999端口需要开放,或者简单点也可以关闭防火墙
systemctl stop firewalld
3. 启动springboot项目时,默认占用一个终端,如果终端窗口关闭,服务进程结束,如何解决?
nohup java -jar boot_data.jar &
nohub java -jar boot-data.jar > 1.log
# 加了nohup后,即使关掉命令窗口,后台程序boot-data.jar也会一直执行
18-SpringBoot2高级-服务部署-war包部署
目的:能够使用war包方式部署SpringBoot项目
步骤:
1、更改打包方式为 war
2、配置打包插件
<!-- 注意:需要将web依赖中的tomcat移除 -->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId><exclusions><exclusion><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-tomcat</artifactId></exclusion></exclusions>
</dependency>
<!--如果保存:Error:(13,8) java: 无法访问javax.servlet.ServletException-->
<dependency><groupId>javax.servlet</groupId><artifactId>servlet-api</artifactId><version>2.5</version><scope>provided</scope>
</dependency><build><!--jar 包名称--><finalName>boot_data</finalName><plugins><plugin><groupId>org.springframework.boot</groupId><artifactId>spring-boot-maven-plugin</artifactId></plugin><!-- 声明打包时,不需要web.xml --><plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-war-plugin</artifactId><configuration><failOnMissingWebXml>false</failOnMissingWebXml></configuration></plugin></plugins>
</build>
3、修改引导类 继承 SpringBootServletInitializer
package com.xxx;import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.AutoConfigurationExcludeFilter;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.context.TypeExcludeFilter;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.FilterType;
import org.springframework.web.bind.annotation.RestController;import java.util.Arrays;/*
* 启动类要继承SpringBootServletInitializer
* 并重写configure方法
* */
@SpringBootApplication
public class HelloApplication extends SpringBootServletInitializer {public static void main(String[] args) {SpringApplication.run(HelloApplication.class, args);}@Overrideprotected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {return builder.sources(HelloApplication.class);}
}
4、配置tomcat,war复制到 webapps 目录下:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RjuYzX69-1644246254860)(assets/image-20210504160435002.png)]
5、启动tomcat
./startup.sh
6、浏览器访问:http://192.168.200.150:8080/boot_data
实际开发中用哪一种?
如果你的工程用户访问量少(不会面临3高问题:高可用 高并发 高性能),那么推荐使用jar包部署方式,因为部署简单;
如果工程面临3高问题,那么推荐使用war包部署,因为使用外部的tomcat,可以做到最大程度的参数自定义(方便tomcat的优化==》运维人员介入)
总结
【1】如何实现被@Configuration修饰的类中的方法产生的bean是单例还是多例?
proxyBeanMethods=true: Full模式,单例模式,底层被 cglib代理,先从IOC容器中检查当前的bean是否存在,如何存在,则直接返回bean对象,否则创建;
proxyBeanMethods=false:LITE模式,多例模式
【2】Import注解导入bean的4种方式
1.直接导入某个类,作为换一个bean被ioc容器管理
2.导入配置类(配置类可以不写@Configuration注解)
3.导入实现ImportSelector接口的实现类(批量导入)
4.导入实现ImportBeanDefinitionRegistrar接口的实现类(批量注册bean信息,完成导入)
【3】常用的条件装配注解有哪些?
@ConditionalOnBean: 容器中存在bean则创建
@ConditionalOnMissingBean: 容器中不存在bean则创建
@ConditionalOnClass:判断某个类必须存在,才创建
@ConditionalOnMissingClass:判断某个类不必须存在,才创建
@ConditionalOnProperty(prefix="前缀",name="名称",havingvalue="必须是指定的值")配置文件中必须存在指定的key和value值则创建
【4】自定装配的原理:
1)SpringBoot基于SPI思想约定工程以启动加载工程系统环境下META-INF/spring.factories文件获取可自动装配的配置类信息;
2)SringBoot引入了条件装配的概念,这些自动装配类只加载满足条件的配置类;
3)通过自动装配的配置类,将相关的资源加入IOC容器,容器中有了这些bean资源,就有了指定的功能;
【5】自定义starter流程
1.定义一个maven工程,打包方式jar,然后引入spring-boot-starter.jar提供spring核心环境依赖;
2.定义属性配置类,一般使用@ConfigurationProperties注解映射yml中的配置信息;
3.定义自动装配的配置类,主要注解:类上:@Configuration(proxyBeanMethods=false):加载快@ConditionalOnxxx:条件装配条件@EnableConfigurationProperties:将属性配置类加载到IOC容器下方法上:@Bean@ConditionalOnxxx:满足条件,则方法被执行,构建对应的bean对象
4.在resources包下定义META-INF/spring.factories文件eg:org.springframework.boot.autoconfigure.EnableAutoConfiguration=\com.myredis.config.MyRedisAutoConfiguration
5.打包
如若内容造成侵权/违法违规/事实不符,请联系编程学习网邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
相关文章
- 2022寒假作业做题记录
## 2022/1/17 #### P1901 单调栈从前往后,从后往前跑两遍,统计接收的能量值,再找最大值即可。 #### P1484 将每一个点与左右连好边,再放入大根堆中,从堆顶逐个取出,再将其左右连接的点的置加一起再减去…...
2024/4/13 12:14:10 - 计算机那么好,为什么很多同学毕业都转行不搞计算机了?
写在前面 目前最火的理工科专业绝对是计算机专业,计算机行业的薪资也是在去年达到了新高,国内大厂的白菜价统一达到了30万以上的年薪。但是就是这么好的行业,每年都会有不少计算机专业出身的人毕业转行不搞计算机,这是为什么呢&a…...
2024/4/13 12:14:05 - 异常分类Exception
...
2024/4/27 22:45:54 - Vue 3.0 组件基础(下)
一、props 验证 1. 对象类型的 props 节点 使用对象类型的 props 节点,可以对每个 prop 进行数据类型的校验。 使用数组类型的 props 节点的缺点:无法为每个 prop 指定具体的数据类型。 2. props 验证方案 2.1 基础类型检查 直接为组件的 prop 属性…...
2024/4/18 6:20:25 - Redis的内存淘汰算法
Redis的内存满了怎么办? 实际上Redis定义了「8种内存淘汰策略」用来处理redis内存满的情况: 在Redis中是可以设置内存最大限制的,因此我们不用担心Redis占满机器的内存影响其他服务,这个参数maxmemory是可以配置的,max…...
2024/4/15 4:31:18 - 嵌入式中5个难查的软件问题
在嵌入式开发软件中查找和消除潜在的错误是一项艰巨的任务。 通常需要英勇的努力和昂贵的工具才能从观察到的崩溃,死机或其他计划外的运行时行为追溯到根本原因。 在最坏的情况下,根本原因会破坏代码或数据,使系统看起来仍然可以正常工作或至…...
2024/4/23 3:15:04 - java常见面试题(附带答案)
这个是照搬这篇博客的内容,顺便附上面试题的答案,方便自己看 Java 最常见的 200 面试题:面试必备_Java中文社群-CSDN博客_java面试题 目录 一、Java 基础 二、容器 一、Java 基础 1. JDK 和 JRE 有什么区别? JDK:J…...
2024/4/20 11:07:16 - 【图神经网络】图神经网络(GNN)学习笔记:GNN的应用简介
TOC GNN的应用简述 GNN的适用范围非常广泛: 显式关联结构的数据:药物分子、电路网络等隐式关联结构的数据:图像、文本等 生物化学领域中:分子指纹识别、药物分子设计、疾病分类等 交通领域中:对交通需求的预测、对…...
2024/4/13 12:13:55 - 旧笔记整理:锁
文章目录线程的几个状态以及转换。设计模式java简单的内存结构:lock与synchronize的区别:synchoronized的内部实现:synchoronized的缺点:什么时候用synchronized,什么时候用lock线程的状态和他们的转换:锁的…...
2024/4/22 12:03:15 - 【周志华机器学习】强化学习
第十六章 强化学习任务与奖赏K-摇臂赌博机e-贪心Softmax有模型学习策略评估策略改进策略迭代与值迭代免模型学习蒙特卡罗强化学习时序差分学习值函数近似模仿学习任务与奖赏 种瓜有许多步骤,但在种瓜的过程中,某些操作并不能立即得到最终奖励࿰…...
2024/4/19 18:47:14 - C#的AutoGui,功能类似Python的pyautogui
Python有一个可以操作键盘鼠标的库,众所周知,pyautogui,非常好用,但是只有Python的版本,搜寻了一下C#有没有类似的库,结果没有找到,于是自己就仿照部分功能封装了一下。封装的不是很好ÿ…...
2024/4/28 11:08:08 - java数据结构:插入排序
插入排序: 从下面动图可以看出,插入排序的主旨思想是在一个有序的排列中插入一个元素,默认认为第一个是有序,从后面的元素中比较和前面已经排好序的元素挨个比较,插入合适的位置;因此需要一个循环(外层循环…...
2024/4/18 17:57:51 - Git使用 从入门到入土 收藏吃灰系列(五) Git本地仓库搭建
📢📢📢📣📣📣 哈喽!大家好,我是【小张同学】,一位上进心十足的博主!😜😜😜 ✨【小张同学】的写作风格:喜欢用【…...
2024/4/15 21:21:04 - Python-float 0.1+0.2为什么不等于0.3
运行如下: 原理: 举个例子,float类型39.29。在计算机存储时,它会先把整数部分39转换成二级制,至于后面的0.29则会一直将它乘以2,如果大于1则减去一继续乘以2,如果等于1则停止。 这样就难免出现…...
2024/4/19 10:34:46 - 【视觉检测C++接口实现】vs2019使用动态链接库yolo_cpp_dll调用yolov3
目录 0. 前言 1. 准备工作 1.1 yolo_cpp_dll.dll和yolo_cpp_dll.lib的获取 1.2 pthreadGC2.dll和pthreadVC2.dll的获取 1.3 yolo_v2_class.hpp的获取 1.4 设置opencv环境变量(若已经设置可忽略) 2. C新项目的创建 2.1 创建一个C新项目࿰…...
2024/4/16 0:05:13 - 2021到2022,从学生成长为职场人(面试打工指南)
2021到2022,从学生成长为职场人 春招实习入字节 春招能进入字节,可以说是今年来一个很重要的转折点。刚进入大三的时候大概三月份,我还不是很紧迫,感觉距离春招还有一段时间,可以继续拉长战线慢慢来。但突然得知同学…...
2024/4/13 12:14:45 - 《ZLMediaKit源码学习笔记》(2)MediaServer作为RTSP转发服务器
系列文章目录 《ZLMediaKit源码学习笔记》(1)windows下VS2022源码编译 《ZLMediaKit源码学习笔记》(2)MediaServer作为RTSP转发服务器(本文) 前言 学习源码前,我们需要先熟悉如何使用ZLMedia…...
2024/4/28 9:38:46 - 学习-Java类和对象之对象数组(22)
任务描述 本关任务:定义一个 Dog 类,使用对象数组的方式创建 3 个 Dog 对象。 相关知识 所谓的对象数组,就是指包含了一组相关的对象。在使用对象数组的时候,一定要清楚一点:一定要先为数组开辟空间。因为其是引用数…...
2024/4/13 12:14:55 - 求子矩阵最大累加和
题目如下: 输入在一行给出两个数n,m,代表矩阵的行和列。而后的每n行,每一行给出m个数,数值有正有负,也可能是0。 输出在一行给出子矩阵的最大累加和。 给出一个案例。 输入: 3 3 -90 48 78 64 -40 64…...
2024/4/18 20:18:47 - 2021.02.07总结
1.自我介绍模板: 面试官您好,我叫XXX,来自XX(籍贯),20年毕业于XXX大学,毕业证和学位证都有,是全日制统招本科。英语有四级证,一般的英文文档能够独立阅读。毕业之后一直在XX(市)XX公司从事前端开…...
2024/4/13 12:14:41
最新文章
- 【中级软件设计师】上午题12-软件工程(1):软件工程模型、敏捷方法、软件需求、系统设计
上午题12-软件工程(1) 1 软件过程1.1 CMM 能力成熟度模型1.1 CMMI (建议直接看思维导图) 2 软件过程模型2.1 瀑布模型2.2 增量模型2.3 演化模型2.3.1 原型模型2.3.2 螺旋模型 2.5 喷泉模型 3 统一过程(UP)模型4 敏捷方…...
2024/4/28 16:27:27 - 梯度消失和梯度爆炸的一些处理方法
在这里是记录一下梯度消失或梯度爆炸的一些处理技巧。全当学习总结了如有错误还请留言,在此感激不尽。 权重和梯度的更新公式如下: w w − η ⋅ ∇ w w w - \eta \cdot \nabla w ww−η⋅∇w 个人通俗的理解梯度消失就是网络模型在反向求导的时候出…...
2024/3/20 10:50:27 - cocos 数字滚动、数字过渡动画
代码: //数字滚动 let sdk: any { a: start_score, } tween(sdk).to(1, { a: this.score }, { progress: (start, end, current, time) > { // this.lab.string Math.round(start (end - start) * time) ;//修改页面上的值 // console.log(修改ing, start (…...
2024/4/27 8:49:13 - C# 构建可定时关闭的异步提示弹窗
C# 构建可定时关闭的异步提示弹窗 引言1、调用接口的实现2、自动定时窗口的实现 引言 我们在最常用最简单的提示弹框莫过于MessageBox.Show( )的方法了,但是使用久了之后,你会发现这个MessageBox并不是万能的,有事后并不想客户去点击&#x…...
2024/4/23 6:37:29 - 《c++》多态案例一.电脑组装
一.代码展示 #include <iostream> using namespace std; class CPU { public://抽象计算函数virtual void calculate() 0;};class CVideoCard { public://抽象显示函数virtual void display() 0;}; class Memory { public://抽象存储函数virtual void storage() 0;};…...
2024/4/23 4:46:08 - 【外汇早评】美通胀数据走低,美元调整
原标题:【外汇早评】美通胀数据走低,美元调整昨日美国方面公布了新一期的核心PCE物价指数数据,同比增长1.6%,低于前值和预期值的1.7%,距离美联储的通胀目标2%继续走低,通胀压力较低,且此前美国一季度GDP初值中的消费部分下滑明显,因此市场对美联储后续更可能降息的政策…...
2024/4/28 13:52:11 - 【原油贵金属周评】原油多头拥挤,价格调整
原标题:【原油贵金属周评】原油多头拥挤,价格调整本周国际劳动节,我们喜迎四天假期,但是整个金融市场确实流动性充沛,大事频发,各个商品波动剧烈。美国方面,在本周四凌晨公布5月份的利率决议和新闻发布会,维持联邦基金利率在2.25%-2.50%不变,符合市场预期。同时美联储…...
2024/4/28 3:28:32 - 【外汇周评】靓丽非农不及疲软通胀影响
原标题:【外汇周评】靓丽非农不及疲软通胀影响在刚结束的周五,美国方面公布了新一期的非农就业数据,大幅好于前值和预期,新增就业重新回到20万以上。具体数据: 美国4月非农就业人口变动 26.3万人,预期 19万人,前值 19.6万人。 美国4月失业率 3.6%,预期 3.8%,前值 3…...
2024/4/26 23:05:52 - 【原油贵金属早评】库存继续增加,油价收跌
原标题:【原油贵金属早评】库存继续增加,油价收跌周三清晨公布美国当周API原油库存数据,上周原油库存增加281万桶至4.692亿桶,增幅超过预期的74.4万桶。且有消息人士称,沙特阿美据悉将于6月向亚洲炼油厂额外出售更多原油,印度炼油商预计将每日获得至多20万桶的额外原油供…...
2024/4/28 13:51:37 - 【外汇早评】日本央行会议纪要不改日元强势
原标题:【外汇早评】日本央行会议纪要不改日元强势近两日日元大幅走强与近期市场风险情绪上升,避险资金回流日元有关,也与前一段时间的美日贸易谈判给日本缓冲期,日本方面对汇率问题也避免继续贬值有关。虽然今日早间日本央行公布的利率会议纪要仍然是支持宽松政策,但这符…...
2024/4/27 17:58:04 - 【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响
原标题:【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响近日伊朗局势升温,导致市场担忧影响原油供给,油价试图反弹。此时OPEC表态稳定市场。据消息人士透露,沙特6月石油出口料将低于700万桶/日,沙特已经收到石油消费国提出的6月份扩大出口的“适度要求”,沙特将满…...
2024/4/27 14:22:49 - 【外汇早评】美欲与伊朗重谈协议
原标题:【外汇早评】美欲与伊朗重谈协议美国对伊朗的制裁遭到伊朗的抗议,昨日伊朗方面提出将部分退出伊核协议。而此行为又遭到欧洲方面对伊朗的谴责和警告,伊朗外长昨日回应称,欧洲国家履行它们的义务,伊核协议就能保证存续。据传闻伊朗的导弹已经对准了以色列和美国的航…...
2024/4/28 1:28:33 - 【原油贵金属早评】波动率飙升,市场情绪动荡
原标题:【原油贵金属早评】波动率飙升,市场情绪动荡因中美贸易谈判不安情绪影响,金融市场各资产品种出现明显的波动。随着美国与中方开启第十一轮谈判之际,美国按照既定计划向中国2000亿商品征收25%的关税,市场情绪有所平复,已经开始接受这一事实。虽然波动率-恐慌指数VI…...
2024/4/28 15:57:13 - 【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试
原标题:【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试美国和伊朗的局势继续升温,市场风险情绪上升,避险黄金有向上突破阻力的迹象。原油方面稍显平稳,近期美国和OPEC加大供给及市场需求回落的影响,伊朗局势并未推升油价走强。近期中美贸易谈判摩擦再度升级,美国对中…...
2024/4/27 17:59:30 - 【原油贵金属早评】市场情绪继续恶化,黄金上破
原标题:【原油贵金属早评】市场情绪继续恶化,黄金上破周初中国针对于美国加征关税的进行的反制措施引发市场情绪的大幅波动,人民币汇率出现大幅的贬值动能,金融市场受到非常明显的冲击。尤其是波动率起来之后,对于股市的表现尤其不安。隔夜美国股市出现明显的下行走势,这…...
2024/4/25 18:39:16 - 【外汇早评】美伊僵持,风险情绪继续升温
原标题:【外汇早评】美伊僵持,风险情绪继续升温昨日沙特两艘油轮再次发生爆炸事件,导致波斯湾局势进一步恶化,市场担忧美伊可能会出现摩擦生火,避险品种获得支撑,黄金和日元大幅走强。美指受中美贸易问题影响而在低位震荡。继5月12日,四艘商船在阿联酋领海附近的阿曼湾、…...
2024/4/28 1:34:08 - 【原油贵金属早评】贸易冲突导致需求低迷,油价弱势
原标题:【原油贵金属早评】贸易冲突导致需求低迷,油价弱势近日虽然伊朗局势升温,中东地区几起油船被袭击事件影响,但油价并未走高,而是出于调整结构中。由于市场预期局势失控的可能性较低,而中美贸易问题导致的全球经济衰退风险更大,需求会持续低迷,因此油价调整压力较…...
2024/4/26 19:03:37 - 氧生福地 玩美北湖(上)——为时光守候两千年
原标题:氧生福地 玩美北湖(上)——为时光守候两千年一次说走就走的旅行,只有一张高铁票的距离~ 所以,湖南郴州,我来了~ 从广州南站出发,一个半小时就到达郴州西站了。在动车上,同时改票的南风兄和我居然被分到了一个车厢,所以一路非常愉快地聊了过来。 挺好,最起…...
2024/4/28 1:22:35 - 氧生福地 玩美北湖(中)——永春梯田里的美与鲜
原标题:氧生福地 玩美北湖(中)——永春梯田里的美与鲜一觉醒来,因为大家太爱“美”照,在柳毅山庄去寻找龙女而错过了早餐时间。近十点,向导坏坏还是带着饥肠辘辘的我们去吃郴州最富有盛名的“鱼头粉”。说这是“十二分推荐”,到郴州必吃的美食之一。 哇塞!那个味美香甜…...
2024/4/25 18:39:14 - 氧生福地 玩美北湖(下)——奔跑吧骚年!
原标题:氧生福地 玩美北湖(下)——奔跑吧骚年!让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 啊……啊……啊 两…...
2024/4/26 23:04:58 - 扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!
原标题:扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!扒开伪装医用面膜,翻六倍价格宰客!当行业里的某一品项火爆了,就会有很多商家蹭热度,装逼忽悠,最近火爆朋友圈的医用面膜,被沾上了污点,到底怎么回事呢? “比普通面膜安全、效果好!痘痘、痘印、敏感肌都能用…...
2024/4/27 23:24:42 - 「发现」铁皮石斛仙草之神奇功效用于医用面膜
原标题:「发现」铁皮石斛仙草之神奇功效用于医用面膜丽彦妆铁皮石斛医用面膜|石斛多糖无菌修护补水贴19大优势: 1、铁皮石斛:自唐宋以来,一直被列为皇室贡品,铁皮石斛生于海拔1600米的悬崖峭壁之上,繁殖力差,产量极低,所以古代仅供皇室、贵族享用 2、铁皮石斛自古民间…...
2024/4/28 5:48:52 - 丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者
原标题:丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者【公司简介】 广州华彬企业隶属香港华彬集团有限公司,专注美业21年,其旗下品牌: 「圣茵美」私密荷尔蒙抗衰,产后修复 「圣仪轩」私密荷尔蒙抗衰,产后修复 「花茵莳」私密荷尔蒙抗衰,产后修复 「丽彦妆」专注医学护…...
2024/4/26 19:46:12 - 广州械字号面膜生产厂家OEM/ODM4项须知!
原标题:广州械字号面膜生产厂家OEM/ODM4项须知!广州械字号面膜生产厂家OEM/ODM流程及注意事项解读: 械字号医用面膜,其实在我国并没有严格的定义,通常我们说的医美面膜指的应该是一种「医用敷料」,也就是说,医用面膜其实算作「医疗器械」的一种,又称「医用冷敷贴」。 …...
2024/4/27 11:43:08 - 械字号医用眼膜缓解用眼过度到底有无作用?
原标题:械字号医用眼膜缓解用眼过度到底有无作用?医用眼膜/械字号眼膜/医用冷敷眼贴 凝胶层为亲水高分子材料,含70%以上的水分。体表皮肤温度传导到本产品的凝胶层,热量被凝胶内水分子吸收,通过水分的蒸发带走大量的热量,可迅速地降低体表皮肤局部温度,减轻局部皮肤的灼…...
2024/4/27 8:32:30 - 配置失败还原请勿关闭计算机,电脑开机屏幕上面显示,配置失败还原更改 请勿关闭计算机 开不了机 这个问题怎么办...
解析如下:1、长按电脑电源键直至关机,然后再按一次电源健重启电脑,按F8健进入安全模式2、安全模式下进入Windows系统桌面后,按住“winR”打开运行窗口,输入“services.msc”打开服务设置3、在服务界面,选中…...
2022/11/19 21:17:18 - 错误使用 reshape要执行 RESHAPE,请勿更改元素数目。
%读入6幅图像(每一幅图像的大小是564*564) f1 imread(WashingtonDC_Band1_564.tif); subplot(3,2,1),imshow(f1); f2 imread(WashingtonDC_Band2_564.tif); subplot(3,2,2),imshow(f2); f3 imread(WashingtonDC_Band3_564.tif); subplot(3,2,3),imsho…...
2022/11/19 21:17:16 - 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机...
win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”问题的解决方法在win7系统关机时如果有升级系统的或者其他需要会直接进入一个 等待界面,在等待界面中我们需要等待操作结束才能关机,虽然这比较麻烦,但是对系统进行配置和升级…...
2022/11/19 21:17:15 - 台式电脑显示配置100%请勿关闭计算机,“准备配置windows 请勿关闭计算机”的解决方法...
有不少用户在重装Win7系统或更新系统后会遇到“准备配置windows,请勿关闭计算机”的提示,要过很久才能进入系统,有的用户甚至几个小时也无法进入,下面就教大家这个问题的解决方法。第一种方法:我们首先在左下角的“开始…...
2022/11/19 21:17:14 - win7 正在配置 请勿关闭计算机,怎么办Win7开机显示正在配置Windows Update请勿关机...
置信有很多用户都跟小编一样遇到过这样的问题,电脑时发现开机屏幕显现“正在配置Windows Update,请勿关机”(如下图所示),而且还需求等大约5分钟才干进入系统。这是怎样回事呢?一切都是正常操作的,为什么开时机呈现“正…...
2022/11/19 21:17:13 - 准备配置windows 请勿关闭计算机 蓝屏,Win7开机总是出现提示“配置Windows请勿关机”...
Win7系统开机启动时总是出现“配置Windows请勿关机”的提示,没过几秒后电脑自动重启,每次开机都这样无法进入系统,此时碰到这种现象的用户就可以使用以下5种方法解决问题。方法一:开机按下F8,在出现的Windows高级启动选…...
2022/11/19 21:17:12 - 准备windows请勿关闭计算机要多久,windows10系统提示正在准备windows请勿关闭计算机怎么办...
有不少windows10系统用户反映说碰到这样一个情况,就是电脑提示正在准备windows请勿关闭计算机,碰到这样的问题该怎么解决呢,现在小编就给大家分享一下windows10系统提示正在准备windows请勿关闭计算机的具体第一种方法:1、2、依次…...
2022/11/19 21:17:11 - 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”的解决方法...
今天和大家分享一下win7系统重装了Win7旗舰版系统后,每次关机的时候桌面上都会显示一个“配置Windows Update的界面,提示请勿关闭计算机”,每次停留好几分钟才能正常关机,导致什么情况引起的呢?出现配置Windows Update…...
2022/11/19 21:17:10 - 电脑桌面一直是清理请关闭计算机,windows7一直卡在清理 请勿关闭计算机-win7清理请勿关机,win7配置更新35%不动...
只能是等着,别无他法。说是卡着如果你看硬盘灯应该在读写。如果从 Win 10 无法正常回滚,只能是考虑备份数据后重装系统了。解决来方案一:管理员运行cmd:net stop WuAuServcd %windir%ren SoftwareDistribution SDoldnet start WuA…...
2022/11/19 21:17:09 - 计算机配置更新不起,电脑提示“配置Windows Update请勿关闭计算机”怎么办?
原标题:电脑提示“配置Windows Update请勿关闭计算机”怎么办?win7系统中在开机与关闭的时候总是显示“配置windows update请勿关闭计算机”相信有不少朋友都曾遇到过一次两次还能忍但经常遇到就叫人感到心烦了遇到这种问题怎么办呢?一般的方…...
2022/11/19 21:17:08 - 计算机正在配置无法关机,关机提示 windows7 正在配置windows 请勿关闭计算机 ,然后等了一晚上也没有关掉。现在电脑无法正常关机...
关机提示 windows7 正在配置windows 请勿关闭计算机 ,然后等了一晚上也没有关掉。现在电脑无法正常关机以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容,让我们赶快一起来看一下吧!关机提示 windows7 正在配…...
2022/11/19 21:17:05 - 钉钉提示请勿通过开发者调试模式_钉钉请勿通过开发者调试模式是真的吗好不好用...
钉钉请勿通过开发者调试模式是真的吗好不好用 更新时间:2020-04-20 22:24:19 浏览次数:729次 区域: 南阳 > 卧龙 列举网提醒您:为保障您的权益,请不要提前支付任何费用! 虚拟位置外设器!!轨迹模拟&虚拟位置外设神器 专业用于:钉钉,外勤365,红圈通,企业微信和…...
2022/11/19 21:17:05 - 配置失败还原请勿关闭计算机怎么办,win7系统出现“配置windows update失败 还原更改 请勿关闭计算机”,长时间没反应,无法进入系统的解决方案...
前几天班里有位学生电脑(windows 7系统)出问题了,具体表现是开机时一直停留在“配置windows update失败 还原更改 请勿关闭计算机”这个界面,长时间没反应,无法进入系统。这个问题原来帮其他同学也解决过,网上搜了不少资料&#x…...
2022/11/19 21:17:04 - 一个电脑无法关闭计算机你应该怎么办,电脑显示“清理请勿关闭计算机”怎么办?...
本文为你提供了3个有效解决电脑显示“清理请勿关闭计算机”问题的方法,并在最后教给你1种保护系统安全的好方法,一起来看看!电脑出现“清理请勿关闭计算机”在Windows 7(SP1)和Windows Server 2008 R2 SP1中,添加了1个新功能在“磁…...
2022/11/19 21:17:03 - 请勿关闭计算机还原更改要多久,电脑显示:配置windows更新失败,正在还原更改,请勿关闭计算机怎么办...
许多用户在长期不使用电脑的时候,开启电脑发现电脑显示:配置windows更新失败,正在还原更改,请勿关闭计算机。。.这要怎么办呢?下面小编就带着大家一起看看吧!如果能够正常进入系统,建议您暂时移…...
2022/11/19 21:17:02 - 还原更改请勿关闭计算机 要多久,配置windows update失败 还原更改 请勿关闭计算机,电脑开机后一直显示以...
配置windows update失败 还原更改 请勿关闭计算机,电脑开机后一直显示以以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容,让我们赶快一起来看一下吧!配置windows update失败 还原更改 请勿关闭计算机&#x…...
2022/11/19 21:17:01 - 电脑配置中请勿关闭计算机怎么办,准备配置windows请勿关闭计算机一直显示怎么办【图解】...
不知道大家有没有遇到过这样的一个问题,就是我们的win7系统在关机的时候,总是喜欢显示“准备配置windows,请勿关机”这样的一个页面,没有什么大碍,但是如果一直等着的话就要两个小时甚至更久都关不了机,非常…...
2022/11/19 21:17:00 - 正在准备配置请勿关闭计算机,正在准备配置windows请勿关闭计算机时间长了解决教程...
当电脑出现正在准备配置windows请勿关闭计算机时,一般是您正对windows进行升级,但是这个要是长时间没有反应,我们不能再傻等下去了。可能是电脑出了别的问题了,来看看教程的说法。正在准备配置windows请勿关闭计算机时间长了方法一…...
2022/11/19 21:16:59 - 配置失败还原请勿关闭计算机,配置Windows Update失败,还原更改请勿关闭计算机...
我们使用电脑的过程中有时会遇到这种情况,当我们打开电脑之后,发现一直停留在一个界面:“配置Windows Update失败,还原更改请勿关闭计算机”,等了许久还是无法进入系统。如果我们遇到此类问题应该如何解决呢࿰…...
2022/11/19 21:16:58 - 如何在iPhone上关闭“请勿打扰”
Apple’s “Do Not Disturb While Driving” is a potentially lifesaving iPhone feature, but it doesn’t always turn on automatically at the appropriate time. For example, you might be a passenger in a moving car, but your iPhone may think you’re the one dri…...
2022/11/19 21:16:57