Spring中IOC容器常用的接口和具体的实现类
在Spring框架没有出现之前,在Java语言中,程序员们创建对象一般都是通过关键字new来完成,那时流行一句话“万物即可new,包括女朋友”。但是这种创建对象的方式维护成本很高,而且对于类之间的相互关联关系很不友好。鉴于这种情况,Spring框架应运而生,Spring框架绝对是一款伟大、设计优秀的框架,它的底层设计思想和应用策略使它一直火热到现在,并逐渐发展成为Spring生态。本篇内容就为大家来介绍下Spring框架中IOC容器相关的接口和API解析。
一、IOC思想介绍
IOC,其实是Inversion of Control单词的缩写,中文的意思是控制反转,也被称为依赖注入(DI)。这是一个过程,就是翻转资源获取的方向。把我们自己创建资源、向环境索取资源变成环境将资源准备好,我们享受资源注入。
IOC容器介绍
在Spring框架提供的功能模块中有一个功能叫做核心容器(Core Container)功能,这个核心容器的作用就是在Spring环境下使用任何功能都必须基于IOC容器。而这里的IOC容器主要包含管理组件对象的生命周期、实例化组件对象、管理组件对象之间的依赖关系等。该容器的设计替程序员屏蔽了组件创建过程中的大量细节,极大的降低了使用门槛,大幅度提高了开发效率。
该容器的主要实现依赖于工厂模式(BeanFactory)+反射。
IOC容器类型
上述IOC容器介绍中说到,IOC容器主要是依赖于工厂模式+反射,在Spring框架中,其实也确实为我们提供了一个顶层接口:BeanFactory工厂接口。该接口是顶层接口,其内部提供了能够管理任何类型对象的高级配置机制(API)。
API介绍如下:
public interface BeanFactory {
/**
* 用于取消引用FactoryBean实例,并将其与FactoryBean创建的bean区分开来。
*/
String FACTORY_BEAN_PREFIX = "&";
/**
* 返回指定bean的实例,该实例可以是共享的或独立的。此方法允许Spring BeanFactory用作Singleton或Prototype设计模式的替代。* 在Singleton bean的情况下,调用者可以保留对返回对象的引用。将别名转换回相应的规范bean名称。
* @param 命名要检索的bean的名称
* @return bean的一个实例
* @throws 如果没有具有指定名称的bean,抛出
NoSuchBeanDefinitionException
* @throws 如果无法获取bean,抛出BeansException
*/
Object getBean(String name) throws BeansException;
/**
* 返回指定bean的实例,该实例可以是共享的或独立的。
* 与getBean(String)的行为相同,但如果bean不是所需类型,则通过抛出
BeanNotOfRequiredTypeException来提供类型安全性的度量。
* 这意味着在转换结果正确时不能抛出ClassCastException,就像#getBean(String)一样。将别名转换回相应的规范bean名称。将询问父工厂是否在此工厂实例中找不到bean。
* @param 命名要检索的bean的名称
* @param bean要匹配的类型,可以是接口或是超类
* @return 一个bean实例
* @throws 如果没有具有指定名称的bean,抛出
NoSuchBeanDefinitionException
* @throws 如果bean不是要求的类型,抛出
BeanNotOfRequiredTypeException
* @throws 如果bean不能创建,抛出BeansException
*/
<T> T getBean(String name, Class<T> requiredType) throws BeansException;
/**
* 返回指定bean的实例,该实例可以是共享的或独立的。
* 允许指定显式构造函数参数/工厂方法参数,覆盖bean定义中指定的默认参数(如果有)。
* @param 命名要检索的bean的名称
* @param args 使用显式参数创建bean实例时使用的参数(仅在创建新实例时应用,而不是在检索现有实例时应用)
* @return 一个bean实例
* @throws 如果没有具有指定名称的bean,抛出
NoSuchBeanDefinitionException
* @throws 如果已经给出了参数但受影响的bean不是Prototype,抛出
BeanDefinitionStoreException
* @throws 如果bean不能创建,抛出BeansException
*/
Object getBean(String name, Object... args) throws BeansException;
/**
* 返回唯一匹配给定对象类型的bean实例(如果有)。此方法进入ListableBeanFactory按类型查找区域,但也可以根据给定类型的名称转换为常规的按名称查找。
* @param bean要匹配的类型,可以是接口或是超类
* @return 匹配所需类型的单个bean的实例
* @throws 如果没有找到给定类型的bean,抛出
NoSuchBeanDefinitionException
* @throws 如果找到多个给定类型的bean,抛出
NoUniqueBeanDefinitionException
* @throws 如果无法创建bean,抛出BeansException
*/
<T> T getBean(Class<T> requiredType) throws BeansException;
/**
* 返回指定bean的实例,该实例可以是共享的或独立的。
* 允许指定显式构造函数参数/工厂方法参数,覆盖bean定义中指定的默认参数(如果有)。此方法进入ListableBeanFactory按类型查找区域,但也可以转换为传统的按名称查找 基于给定类型的名称。
* @param requiredType bean要匹配的类型,可以是接口或是超类
* @param args 使用显式参数创建bean实例时使用的参数(仅在创建新实例时应用,而不是在检索现有实例时应用)
* @return 一个bean实例
* @throws 如果没有找到给定类型的bean,抛出
NoSuchBeanDefinitionException
* @throws 如果已经给出了参数但受影响的bean不是Prototype,抛出
BeanDefinitionStoreException
* @throws 如果无法创建bean,抛出BeansException
* @since 4.1
*/
<T> T getBean(Class<T> requiredType, Object... args) throws BeansException;
/**
* 返回指定bean的提供程序,允许对实例进行惰性按需检索,包括可用性和唯一性选项。
* @param requiredType bean要匹配的类型,可以是接口或是超类
* @return 相应的提供者句柄
*/
<T> ObjectProvider<T> getBeanProvider(Class<T> requiredType);
/**
* 返回指定bean的提供程序,允许对实例进行惰性按需检索,包括可用性和唯一性选项。
* @param requiredType bean要匹配的类型。可以是泛型类型声明。请注意,此处不支持集合类型,与反射注入点相反。* 要以编程方式检索与特定类型匹配的bean列表,请在此处将实际bean类型指定为参数,然后使用
ObjectProvider.orderedStream()或其延迟流/迭代选项。
* @return 相应的提供者句柄
*/
<T> ObjectProvider<T> getBeanProvider(ResolvableType requiredType);
/**
* 此bean工厂是否包含bean定义或具有给定名称的外部注册的bean的singleton实例
* 如果给定的名称是别名,它将被转换回相应的规范bean名称。
* 如果此工厂是分层的,将询问任何父工厂是否在这个工厂实例中找不到bean。如果找到匹配给定名称的bean定义或单例实例,则此方法将返回true。
* 无论命名bean定义是具体的还是抽象的,lazy还是eager的,作用域与否。因此,请注意此方法的true返回值不一定表示getBean将能够获取同名的实例。
* @param name 查询的bean的名称
* @return 给定名称的bean是否存在
*/
boolean containsBean(String name);
/**
* 该Bean是否是共享的单例? 也就是说, getBean()方法总是返回相同的实例
* 注意:返回false的此方法不能清楚地表明是独立的实例。它表示非单例实例,也可以对应于作用域的bean。
* 使用isPrototype操作显式检查是否是独立的实例。将别名转换回相应的规范bean名称。将询问父工厂是否在此工厂实例中找不到bean。
* @param name 查询的bean的名称
* @return 该bean是否有单例实例
* @throws 如果没有给定名称的Bean,抛出
NoSuchBeanDefinitionException
*/
boolean isSingleton(String name) throws NoSuchBeanDefinitionException;
/**
* 该bean是否是Prototype? 也就是说,getBean总会返回独立实例吗
* 注意:返回false的此方法不能清楚地指示单个对象。它表示非独立实例,也可以对应于范围内的bean。
* 使用isSingleton操作显式检查共享单例实例。将别名转换回相应的规范bean名称。将询问父工厂是否在此工厂实例中找不到bean。
* @param name 查询的bean的名称
* @return 这个bean是否总是提供独立的实例
* @throws 如果没有给定名称的Bean,抛出
NoSuchBeanDefinitionException
*/
boolean isPrototype(String name) throws NoSuchBeanDefinitionException;
/**
* 检查具有给定名称的bean是否与指定的类型匹配。更具体地说,检查对给定名称的getBean调用是否将返回可分配给指定目标类型的对象。
* 将别名转换回相应的规范bean的名称.将询问父工厂是否在此工厂实例中找不到bean。
* @param name 查询bean的名称
* @param typeToMatch 要匹配的类型
* @return 如果Bean类型匹配,返回true;如果bean类型不匹配或不确定,返回false。
* @throws 如果没有给定名称的Bean,抛出
NoSuchBeanDefinitionException
*/
boolean isTypeMatch(String name, ResolvableType typeToMatch) throws NoSuchBeanDefinitionException;
/**
* 检查具有给定名称的bean是否与指定的类型匹配。更具体地说,检查对给定名称的getBean调用是否将返回可分配给指定目标类型的对象。
* 将别名转换回相应的规范bean的名称.将询问父工厂是否在此工厂实例中找不到bean。
* @param name 查询bean的名称
* @param typeToMatch 要匹配的类型
* @return 如果Bean类型匹配,返回true;如果bean类型不匹配或不确定,返回false。
* @throws 如果没有给定名称的Bean,抛出
NoSuchBeanDefinitionException
*/
boolean isTypeMatch(String name, Class<?> typeToMatch) throws NoSuchBeanDefinitionException;
/**
* 确定给定名称的bean的类型。进一步来说,确定getBean方法为给定bean名称返回的对象类型。对于FactoryBean,返回FactoryBean创建的对象类型,由FactoryBean.getObjectType()公开。
* 将别名转换回相应的规范bean名称。将询问父工厂是否在此工厂实例中找不到bean。
* @param name 查询的bean的名称
* @return bean的类型, 或者不可确定返回null。
* @throws 如果没有给定名称的Bean,抛出
NoSuchBeanDefinitionException
*/
@Nullable
Class<?> getType(String name) throws NoSuchBeanDefinitionException;
/**
* 返回给定bean名称的别名(如果有)。所有这些别名在getBean调用中使用时指向同一个bean。
* 如果给定名称是别名,则对应原始bean名称和其他别名( 如果有的话)将返回,原始bean名称是数组中的第一个元素。将询问父工厂是否在此工厂实例中找不到bean。
* @param name 用于检查别名的bean名称
* @return 别名,如果没有,则为空数组
*/
String[] getAliases(String name);
}
BeanFactory顶层接口内部设计了上述API方法,所以它需要具体的实现类来实现这些方法,说到具体的实现类,那么我们就需要查看下该接口的子接口和相关实现类。我们借助开发工具IDEA来查看BeanFactory顶层接口的子接口和具体实现。
图解:
我们可以看到,BeanFactory有三大派生的直属接口,分别是:ListableBeanFactory,HierarchicalBeanFactory,AutowireCapableBeanFactory。其中
(1)ListableBeanFactory子接口:提供容器中bean迭代的功能。如返回所有Bean的名字、容器中Bean的数量等。
(2)HierarchicalBeanFactory子接口:提供父容器的访问功能,可通过 ConfigurableBeanFactory的setParentBeanFactory方法设置父容器,主要是为了实现Bean工厂的分层。
其中子容器可通过接口方法访问父容器;通过 HierarchicalBeanFactory 接口, Spring 的 IOC 容器可以建立父子层级关联的容器体系,子容器可以访问父容器中的Bean,但父容器不能访问子容器的Bean。
Spring 使用父子容器实现了很多功能,比如在 Spring MVC 中,展现层Bean位于一个子容器中,而业务层和持久层的Bean位于父容器中。这样,展现层Bean就可引用业务层和持久层的Bean,而业务层和持久层的 Bean 则看不到展现层的Bean。
(3)AutowireCapableBeanFactory子接口:为 Spring 容器之外的Bean ,也就是处理未交由Spring管理的Bean ,提供依赖注入的功能。
二、接口具体分析
HierarchicalBeanFactory接口分析
// 继承BeanFactory接口,父子级联IOC容器的接口
public interface HierarchicalBeanFactory extends BeanFactory {
// 返回父Bean工厂,如果没有,则返回null
@Nullable BeanFactory getParentBeanFactory();
/** 返回本地bean工厂, * 判断是否包含给定名称的bean,忽略父Bean工厂中定义的bean。这是containsBean的替代方案,忽略来自父bean工厂的给定名称的bean。 */
boolean containsLocalBean(String name);}
ListableBeanFactory接口分析
//扩展了BeanFactory接口,提供了对bean的枚举能力,
//即可以返回bean的实例集合,而不用像BeanFactory只能返回单个bean的实例
//注意:如果存在父容器的话该接口不会考虑父容器中的bean,只会返回当前容器中的
beanpublic interface ListableBeanFactory extends BeanFactory {
// 根据Bean的名称,判断容器中是否包含bean的描述信息
boolean containsBeanDefinition(String beanName);
// 获取容器中对应组件对象Bean的描述信息数量
int getBeanDefinitionCount();
// 获取容器中所有组件对象的Bean的描述信息
String[] getBeanDefinitionNames();
// 根据类型获取容器中所有组件对象的bean名称
String[] getBeanNamesForType(ResolvableType type);
String[] getBeanNamesForType(ResolvableType type, boolean includeNonSingletons, boolean allowEagerInit);
String[] getBeanNamesForType(@Nullable Class<?> type);
String[] getBeanNamesForType(@Nullable Class<?> type, boolean includeNonSingletons, boolean allowEagerInit);
// 根据类型 获取容器中的Bean对象
<T> Map<String, T> getBeansOfType(@Nullable Class<T> type) throws BeansException;
<T> Map<String, T> getBeansOfType(@Nullable Class<T> type, boolean includeNonSingletons, boolean allowEagerInit) throws BeansException;
// 根据注解类型,获取容器中Bean组件对象的名称
String[] getBeanNamesForAnnotation(Class<? extends Annotation> annotationType);
Map<String, Object> getBeansWithAnnotation(Class<? extends Annotation> annotationType) throws BeansException;
@Nullable <A extends Annotation> A findAnnotationOnBean(String beanName, Class<A> annotationType) throws NoSuchBeanDefinitionException;}
AutowireCapableBeanFactory接口分析
//扩展了BeanFactory,主要提供了自动装配能力,包含了bean的创建、注入配置、属性配置、依赖解析、后置处理器前后的实例化、bean的实例化、bean的销毁登
public interface AutowireCapableBeanFactory extends BeanFactory {
//无自动装配
int AUTOWIRE_NO = 0;
//by-name装配
int AUTOWIRE_BY_NAME = 1;
//by-type装配
int AUTOWIRE_BY_TYPE = 2;
//constructor构造函数装配
int AUTOWIRE_CONSTRUCTOR = 3;
//自动装配,已被标记为过时
@Deprecated
int AUTOWIRE_AUTODETECT = 4;
// 用给定的class创建一个Bean实例,完整经历一个Bean创建过程的生命周期节点回调,但不执行传统的autowiring
<T> T createBean(Class<T> beanClass) throws BeansException;
// 用于(再次)填充指定Bean被注解的元素或方法(如@Resource @Autowired),不执行传统的autowiring
void autowireBean(Object existingBean) throws BeansException;
// 配置Bean
Object configureBean(Object existingBean, String beanName) throws BeansException;
// 用于细粒度控制bean生命周期的方法
Object createBean(Class<?> beanClass, int autowireMode, boolean dependencyCheck) throws BeansException;
Object autowire(Class<?> beanClass, int autowireMode, boolean dependencyCheck) throws BeansException;
// 将传入的第一个参数按照spring中按name或者按type装备的方法将传入的Bean的各个properties给装配上
void autowireBeanProperties(Object existingBean, int autowireMode, boolean dependencyCheck) throws BeansException;
void applyBeanPropertyValues(Object existingBean, String beanName) throws BeansException;
// 初始化容器中的Bean
Object initializeBean(Object existingBean, String beanName) throws BeansException;
// 对Bean初始化前后应用逻辑处理器
// 执行BeanPostProcessor前置处理逻辑
Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName) throws BeansException;
// 执行BeanPostProcessor后置处理逻辑
Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName) throws BeansException;
// 销毁容器中的Bean
void destroyBean(Object existingBean);
// 根据传入的类型,从Spring容器(包括父子容器)中查找出指定类型下唯一的Bean,并将beanName与beanInstance包装成NamedBeanHolder对象返回
<T> NamedBeanHolder<T> resolveNamedBean(Class<T> requiredType) throws BeansException;
// 解析Bean需要的依赖
@Nullable
Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName) throws BeansException;
@Nullable
Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,@Nullable Set<String> autowiredBeanNames,@Nullable TypeConverter typeConverter) throws BeansException;
}
SimpleJndiBeanFactory实现类分析
该实现类是基于JndiLocatorSupport的BeanFactory实现,并使用HashMap进行缓存处理。
这里需要注意的是SimpleJndiBeanFactory不支持枚举的Bean定义,因此没有实现ListableBeanFactory,而是直接实现的BeanFactory。
ApplicationContext接口分析
通过上述BeanFactory接口层级图,我们可以看到,在HierarchicalBeanFactory接口下,有一子接口叫做ApplicationContext。
这里我们也说一下为什么单独将该接口进行说明。
ApplicationContext隶属于org.springframework.context,它在继承BeanFactory接口的同时,同时还继承了如下接口:
EnvironmentCapable, ListableBeanFactory,HierarchicalBeanFactory,MessageSource, ApplicationEventPublisher, ResourcePatternResolver
使ApplicationContext接口包含了IOC完整实现的同时,还在其基础上扩展了许多功能。比如资源访问、事件机制、国际化(il8n)等。而我们一般都称ApplicationContext接口的具体实现类对象为ApplicationContext上下文,它为我们程序员良好运用Spring框架提供了很好的支持。
ApplicationContext接口源码解析:
public interface ApplicationContext extends EnvironmentCapable, ListableBeanFactory, HierarchicalBeanFactory, MessageSource, ApplicationEventPublisher, ResourcePatternResolver {
// 返回此应用程序上下文的唯一id。返回:上下文的唯一id,如果没有则返回null @Nullable String getId(); // 返回此上下文所属的已部署应用程序的名称。返回:已部署应用程序的名称,默认情况下为空
String String getApplicationName();
// 返回此上下文的友好名称。返回:该上下文的显示名称(从不为空)
String getDisplayName();
// 返回第一次加载此上下文时的时间戳。返回:该上下文第一次加载时的时间戳(毫秒)
getStartupDate();
// 返回父上下文,如果没有父上下文并且这是上下文层次结构的根,则返回null。返回:父上下文,如果没有父上下文则返回null
@Nullable
ApplicationContext getParent();
/**
* 为此上下文公开
AutowireCapableBeanFactory功能。
* 除了初始化位于应用程序上下文之外的bean实例,将Spring bean生命周期(全部或部分)应用于它们之外,应用程序代码通常不使用它。
*/
AutowireCapableBeanFactory getAutowireCapableBeanFactory() throws IllegalStateException;
}
接下来我们分析一下ApplicationContext继承的接口,分析一下这些接口的作用及各自接口内API方法的意义。
EnvironmentCapable接口分析
// EnvironmentCapable提供了getEnvironment方法,获取当前Spring的配置信息(环境变量、application.properties等)
public interface EnvironmentCapable {
// 读取配置资源
Environment getEnvironment();
}
ApplicationEventPublisher接口分析
// 封装事件发布功能的接口
@FunctionalInterfacepublic interface ApplicationEventPublisher {
// 将应用程序事件通知与此应用程序注册的所有匹配侦听器。事件可以是框架事件(例如ContextRefreshedEvent)或特定于应用程序的事件
default void publishEvent(ApplicationEvent event) {
publishEvent((Object) event);
}
// 通知所有与此应用程序注册的事件匹配的侦听器。如果指定的事件不是一个ApplicationEvent,它将被包装在一个PayloadApplicationEvent中
// 这样的事件发布步骤实际上是一个多播程序的交接,并不意味着同步或异步执行,甚至根本不意味着立即执行。我们鼓励事件侦听器尽可能高效,单独使用异步执行来进行长时间运行和可能阻塞的操作。
void publishEvent(Object event);
}
MessageSource接口分析
// 用于解析消息的策略接口,支持此类消息的参数化和国际化
public interface MessageSource {
// 尝试解析该消息。如果没有找到消息,则返回默认消息
@Nullable
String getMessage(String code, @Nullable Object[] args, @Nullable String defaultMessage, Locale locale);
// 尝试解析该消息。如果无法找到该消息,则将其视为错误
String getMessage(String code, @Nullable Object[] args, Locale locale) throws NoSuchMessageException;
// 尝试使用传入的MessageSourceResolvable参数中包含的所有属性来解析消息。
// 注意:我们必须在此方法上抛出NoSuchMessageException,因为在调用此方法时,我们无法确定可解析对象的defaultMessage属性是否为null。
String getMessage(MessageSourceResolvable resolvable, Locale locale) throws NoSuchMessageException;}
ResourcePatternResolver接口分析
/**
* 根据路径或者通配符获取多个资源,用于将位置模式解析为Resource对象的策略接口。
* 可以用于任何类型的位置模式,该接口还建议为类路径中的所有匹配资源添加一个新的资源前缀“classpath:”。
*/
public interface ResourcePatternResolver extends ResourceLoader {
String CLASSPATH_ALL_URL_PREFIX = "classpath*:";
// 用于读取(指定位置下的)配置文件
Resource[] getResources(String locationPattern) throws IOException;
}
总结
上述内容,为大家介绍了BeanFactory顶层接口下其相关子接口具体的作用以及接口提供的抽象api的作用。帮助大家在源码层面理解Spring框架底层结构设计。我们在知晓底层设计结构之后,重点关注应是在ApplicationContext接口及其实现上。
相关文章:
Spring中IOC容器常用的接口和具体的实现类
在Spring框架没有出现之前,在Java语言中,程序员们创建对象一般都是通过关键字new来完成,那时流行一句话“万物即可new,包括女朋友”。但是这种创建对象的方式维护成本很高,而且对于类之间的相互关联关系很不友好。鉴于…...

【MySQL】索引特性
🌠 作者:阿亮joy. 🎆专栏:《零基础入门MySQL》 🎇 座右铭:每个优秀的人都有一段沉默的时光,那段时光是付出了很多努力却得不到结果的日子,我们把它叫做扎根 目录 👉没…...

【深度学习笔记】动量梯度下降法
本专栏是网易云课堂人工智能课程《神经网络与深度学习》的学习笔记,视频由网易云课堂与 deeplearning.ai 联合出品,主讲人是吴恩达 Andrew Ng 教授。感兴趣的网友可以观看网易云课堂的视频进行深入学习,视频的链接如下: 神经网络和…...

《TCP IP网络编程》第十二章
第 12 章 I/O 复用 12.1 基于 I/O 复用的服务器端 多进程服务端的缺点和解决方法: 为了构建并发服务器,只要有客户端连接请求就会创建新进程。这的确是实际操作中采用的一种方案,但并非十全十美,因为创建进程要付出很大的代价。…...

基于CNN卷积神经网络的调制信号识别算法matlab仿真
目录 1.算法运行效果图预览 2.算法运行软件版本 3.部分核心程序 4.算法理论概述 1. 卷积神经网络(CNN) 2. 调制信号识别 3.实现过程 5.算法完整程序工程 1.算法运行效果图预览 2.算法运行软件版本 MATLAB2022A 3.部分核心程序 % 构建调制类型…...
正则,JS:this,同步异步,原型链笔记整理
一 正则表达式 正则表达式(regular expression)是一种表达文本模式(即字符串结构)的方法,有点像字符串的模板,常常用来按照“给定模式”匹配文本 正则表达式可以用于以下常见操作: 匹配&…...
【NOIP】小鱼的数字游戏题解
author:&Carlton tag:递归,栈 topic:【NOIP】小鱼的数字游戏题解 language:C website:洛谷 date:2023年7月29日 目录 我的题解思路 优化 别人的优秀思路: 我的题解思路 题…...

算法的时间复杂度、空间复杂度如何比较?
目录 一、时间复杂度BigO 大O的渐进表示法: 例题一: 例题2: 例题3:冒泡排序的时间复杂度 例题4:二分查找的时间复杂度 书写对数的讲究: 例题5: 实例6: 利用时间复杂度解决编…...
We are the Lights 2023牛客暑期多校训练营4-L
登录—专业IT笔试面试备考平台_牛客网 题目大意:有n*m盏灯,q次操作,每次可以将一整行或一整列的等打开或关闭 1<n,m<1e6;1<q<1e6 思路:对于同一行或者同一列来说,只要最后一次操作时开或者关࿰…...
ant-design-vue中table组件使用customRender渲染v-html
ant-design-vue遇到table中列表数据需要高亮渲染 1、customRender可以使用,但是使用v-html发现不生效还报错 const columns [title: name,dataIndex: name,customRender: (val, row) > {return <span v-html{val}></span>} ]2、customeRender函数…...
若依框架实现后端防止用户重复点击
若依框架实现后端防止用户重复点击 基于自定义注解、切面、Redis实现 1. 添加自定义注解: 代码放置位置:com/ruoyi/common/annotation/RepeatClick.java time: 时间默认0; unit:单位默认 秒; key: 默认空字符串 package com.ruoyi.fra…...
PCA对手写数字数据集的降维
手写数字的数据集结构为(42000, 784),用KNN跑一次半小时,得到准确率在96.6%上下,用随机森林跑一次12秒,准确率在93.8%,虽然KNN效果好,但由于数据量太大,KNN计算太缓慢,所以我们不得不选用随机森林。我们使用了各种技术对手写数据集进行特征选择,最后使用嵌入 法Select…...

Python入门【变量的作用域(全局变量和局部变量)、参数的传递、浅拷贝和深拷贝、参数的几种类型 】(十一)
👏作者简介:大家好,我是爱敲代码的小王,CSDN博客博主,Python小白 📕系列专栏:python入门到实战、Python爬虫开发、Python办公自动化、Python数据分析、Python前后端开发 📧如果文章知识点有错误…...

下级平台级联安防视频汇聚融合EasyCVR平台,层级显示不正确是什么原因?
视频汇聚平台安防监控EasyCVR可拓展性强、视频能力灵活、部署轻快,可支持的主流标准协议有GB28181、RTSP/Onvif、RTMP等,以及厂家私有协议与SDK接入,包括海康Ehome、海大宇等设备的SDK等,能对外分发RTSP、RTMP、FLV、HLS、WebRTC等…...
vue : 无法加载文件 C:\Users\jianfei\AppData\Roaming\npm\vue.ps1,因为在此系统上禁止运行脚本。...
背景 在新电脑上配置vue环境 PS E:\CODE_PROJ\myvue\vue23\P61_使用脚手架\vue_test> npm install -g vue/cli npm WARN deprecated source-map-url0.4.1: See https://github.com/lydell/source-map-url#deprecated npm WARN deprecated urix0.1.0: Please see https://git…...
godot引擎c++源码深度解析系列二
记录每次研究源码的突破,今天已经将打字练习的功能完成了一个基本模型,先来看下运行效果。 godot源码增加打字练习的demo 这个里面需要研究以下c的控件页面的开发和熟悉,毕竟好久没有使用c了,先来看以下代码吧。 //第一排 显示文本…...
专才or 通才
前言 不知道大家有没有这样的感觉,现在的工作专业化程度越来越高,而且是细分方向越来越小。IT领域分到你是计算里面的数据库或者了流式计算引擎,或者是协议存储还是KV存储引擎。 专业化的优势 专业化的程度带来了一个好处就是你在这个领域…...

【小白必看】Python爬虫实战之批量下载女神图片并保存到本地
文章目录 前言运行结果部分图片1. 引入所需库2. 发送请求获取网页内容3. 解析网页内容并提取图片地址和名称4. 下载并保存图片完整代码关键代码讲解 结束语 前言 爬取网络上的图片是一种常见的需求,它可以帮助我们批量下载大量图片并进行后续处理。本文将介绍如何使…...

道本科技||全面建立国有企业合规管理体系
为全面深化国有企业法治建设,不断加强合规管理,防控合规风险,保障企业稳健发展,近日,市国资委印发《常州市市属国有企业合规管理办法(试行)》(以下简称《办法》)…...
CentOS 8上安装和配置Redis
在本篇博客中,我们将演示如何在CentOS 8上安装和配置Redis。我们将首先安装Redis,然后配置Redis以设置密码并允许公开访问。 步骤 1:安装Redis 首先,更新软件包列表: sudo yum update安装Redis: sudo yum …...
web vue 项目 Docker化部署
Web 项目 Docker 化部署详细教程 目录 Web 项目 Docker 化部署概述Dockerfile 详解 构建阶段生产阶段 构建和运行 Docker 镜像 1. Web 项目 Docker 化部署概述 Docker 化部署的主要步骤分为以下几个阶段: 构建阶段(Build Stage):…...
Android Wi-Fi 连接失败日志分析
1. Android wifi 关键日志总结 (1) Wi-Fi 断开 (CTRL-EVENT-DISCONNECTED reason3) 日志相关部分: 06-05 10:48:40.987 943 943 I wpa_supplicant: wlan0: CTRL-EVENT-DISCONNECTED bssid44:9b:c1:57:a8:90 reason3 locally_generated1解析: CTR…...

超短脉冲激光自聚焦效应
前言与目录 强激光引起自聚焦效应机理 超短脉冲激光在脆性材料内部加工时引起的自聚焦效应,这是一种非线性光学现象,主要涉及光学克尔效应和材料的非线性光学特性。 自聚焦效应可以产生局部的强光场,对材料产生非线性响应,可能…...

从WWDC看苹果产品发展的规律
WWDC 是苹果公司一年一度面向全球开发者的盛会,其主题演讲展现了苹果在产品设计、技术路线、用户体验和生态系统构建上的核心理念与演进脉络。我们借助 ChatGPT Deep Research 工具,对过去十年 WWDC 主题演讲内容进行了系统化分析,形成了这份…...

基于ASP.NET+ SQL Server实现(Web)医院信息管理系统
医院信息管理系统 1. 课程设计内容 在 visual studio 2017 平台上,开发一个“医院信息管理系统”Web 程序。 2. 课程设计目的 综合运用 c#.net 知识,在 vs 2017 平台上,进行 ASP.NET 应用程序和简易网站的开发;初步熟悉开发一…...
深入浅出:JavaScript 中的 `window.crypto.getRandomValues()` 方法
深入浅出:JavaScript 中的 window.crypto.getRandomValues() 方法 在现代 Web 开发中,随机数的生成看似简单,却隐藏着许多玄机。无论是生成密码、加密密钥,还是创建安全令牌,随机数的质量直接关系到系统的安全性。Jav…...
线程与协程
1. 线程与协程 1.1. “函数调用级别”的切换、上下文切换 1. 函数调用级别的切换 “函数调用级别的切换”是指:像函数调用/返回一样轻量地完成任务切换。 举例说明: 当你在程序中写一个函数调用: funcA() 然后 funcA 执行完后返回&…...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...

PL0语法,分析器实现!
简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...
Spring Boot+Neo4j知识图谱实战:3步搭建智能关系网络!
一、引言 在数据驱动的背景下,知识图谱凭借其高效的信息组织能力,正逐步成为各行业应用的关键技术。本文聚焦 Spring Boot与Neo4j图数据库的技术结合,探讨知识图谱开发的实现细节,帮助读者掌握该技术栈在实际项目中的落地方法。 …...