一些Spring的理解

说说你对Spring的理解

  • 首先Spring是一个生态:可以构建企业级应用程序所需的一切基础设施

  • 但是,通常Spring指的就是Spring Framework,它有两大核心:

  1. IOC和DI

    它的核心就是一个对象管理工厂容器,Spring工厂用于生产Bean,和管理Bean的生命周期,通过控制反转和依赖注入的方式实现系统的高内聚低耦合设计

    • 最小的代价和最小的侵入性使松散的耦合得以实现
    • Bean可以饿汉式和懒加载
    • 集中管理了对象

    实现机制:

    • 简单工厂设计模式:(BeanFactory.getBean())
    • 反射:使用反射创建的对象
  2. AOP

    1. 面向切面编程,允许我们将横切关注点从核心业务逻辑中分离出来,实现代码的模块化和重用。可以方便的实现对程序进行权限拦截、运行监控、日志记录等切面功能。

除了这两大核心还提供了丰富的功能和模块, 数据访问、事务管理、Web开发等。数据访问模块提供了对数据库的访问支持,可以方便地进行数据库操作。事务管理模块提供了对事务的管理支持,确保数据的一致性和完整性。Web开发模块则提供了构建Web应用程序的工具和框架,简化了Web开发的过程。

IOC的实现机制

  • Spring的IoC底层实现机制主要依赖于反射、配置元数据、Bean定义、Bean工厂和依赖注入等技术和组件。通过这些机制,Spring实现了Bean的创建、配置和管理,以及Bean之间的解耦和依赖注入

IOC的加载流程

本质就是Bean的创建过程,分为4个大阶段,Bean通过代码或者XML或者注解进行定义后,从BeanDefintion中加载到内存,通过BeanDefintion中的全类名反射获取到对象,然后会进行依赖的注入进行使用

  1. 在进行new AnnotationConfigApplicationContext()的时候开始加载
  2. 调用BeanFactoryPostProessors(Bean工厂后置处理器)进行扫描,循环将各种类信息转换为BeanDefintion
  3. 将BeanDefintion缓存到BeanDefintionMap中,方便后面实例化的时候使用
  4. BeanFactory通过加载BeanDefintion开始生产Bean,生产前会检查Bean是否合法:是否为单例的,是否为懒加载,是不是抽象的,如果完成了验证则需要推断构造方法,因为Spring的实例化是通过构造方法反射进行的
    • 然后找到存储Bean的各级缓存,通过类名去找,如果找到就不创建
    • 如果没有找到就通过反射进行实例化
  5. 然后判断是否需要属性注入,如果需要注入则将实例化的对象进行属性进行依赖注入(DI)
  6. 调用Aware回调,调用生命周期的回调,接着对类进行增强AOP等
  7. 然后将Bean放进单例池,存到容器中

AOP的加载流程

  1. 在Spring启动时,会通过AspectJ来解析切点表达式,然后根据目标是否实现接口来决定代理方式
  2. 在调用阶段,Spring会通过责任链模式来管理通知的执行顺序,通知包括,前置通知,后置通知,异常通知,最终通知和环绕通知,它们会按照配置的顺序来执行

解释Spring中bean的生命周期

Bean生命周期:指定的就是Bean从创建到销毁的整个过程: 分4大步:

  1. 实例化
    a. 通过反射去推断构造函数进行实例化
    b. 实例工厂、 静态工厂
  2. 依赖注入(DI)
    a. 解析自动装配(byname bytype constractor none @Autowired
  3. 初始化
    a. 调用很多Aware回调方法
    b. 调用BeanPostProcessor.postProcessBeforeInitialization
    c. 调用生命周期回调初始化方法
    d. 调用BeanPostProcessor.postProcessAfterInitialization, 如果bean实现aop则会在这里创建动态代理
  4. 销毁
    a. 在spring容器关闭的时候进行调用
    b. 调用生命周期回调销毁方法

Spring的三级缓存

  1. singletonObjects缓存:这是一级缓存,也被称为“单例池”,用于存储完全初始化完成的单例Bean的实例对象。当Bean被完全初始化并创建后,它会被放入这个缓存中,供后续请求直接获取,避免重复创建。
  2. earlySingletonObjects缓存:这是二级缓存,用于存储尚未完全初始化完成的单例Bean的早期引用。在某些情况下,当一个Bean在创建过程中需要引用另一个尚未完全初始化的Bean时,这个尚未完全初始化的Bean的早期引用就会被放入这个缓存中,以解决循环依赖的问题。
  3. singletonFactories缓存:这是三级缓存,也被称为“单例工厂池”,用于存储用于创建单例Bean的ObjectFactory。在创建单例Bean时,如果发现该Bean依赖于其他的Bean,则需要先创建该依赖的Bean实例,此时Spring会将用于创建该依赖的ObjectFactory保存到三级缓存中。

在Bean的创建过程中,Spring会首先检查三级缓存中是否存在对应的BeanDefinition对象。如果存在,则直接使用该对象来创建Bean实例;如果不存在,则会继续从二级缓存、一级缓存以及父容器中查找

ApplicationContext

  • Spring是Spring的上下文,本质是一个容器,实现了BeanFactory
  • 不会主动生产Bean,而是通知BeanFactory去进行生产
  • 能加载环境变量
  • 支持多语言
  • 实现事件的监听

BeanDefintion

存储的临时的Bean的定义信息,将Bean的定义信息解析后传递给BeanFactory进行对象的生产

BeanFactory 和 FactroyBean 的区别

  1. BeanFactory:

    • 是Spring框架的核心接口之一,用于管理和获取Bean实例。

    • 是一个容器,负责实例化、配置和管理Bean对象。

    • 提供了一系列的方法用于获取Bean,如根据名称获取Bean、根据类型获取Bean等。

    • 可以延迟加载Bean实例,只在使用时才进行实例化。

  2. FactoryBean:

    • 是一个特殊的Bean,实现了FactoryBean接口。

    • 用于自定义Bean的实例化逻辑,可以通过FactoryBean创建复杂的Bean实例。

    • FactoryBean的实现类可以定义自己的逻辑来创建和管理Bean对象,并将其作为一个普通Bean注册到Spring容器中。

    • 在从容器中获取FactoryBean时,实际上获取到的是FactoryBean创建的对象,而不是FactoryBean本身。

Autowired 和 Resource 的区别

@Autowired和@Resource都是用于依赖注入的注解,用于将其他组件或资源自动注入到目标对象中。它们在使用方式和功能上有一些区别:

  1. @Autowired:

    • 是Spring框架的注解,基于类型进行依赖注入。

    • 默认按照类型进行匹配注入,如果存在多个匹配类型的Bean,则根据属性名称进行匹配。

    • 可以用于构造器、字段、方法或者参数上。

    • 支持通过@Qualifier注解指定具体的Bean名称进行注入。

  2. @Resource:

    • 是Java EE规范中定义的注解,在Java 6及以上版本中可用。

    • 基于名称进行依赖注入,先按照名称查找,再按照类型匹配。

    • 默认按照属性名称进行查找,也可以通过name属性指定具体的Bean名称进行注入。

    • 只能用于字段、setter方法或者参数上。

Spring 用到了哪些设计模式

  1. 单例模式:Spring默认使用单例模式来管理和创建Bean对象,确保在整个应用中只有一个实例存在。
  2. 工厂模式:Spring使用工厂模式来创建和管理Bean实例,通过BeanFactory或ApplicationContext等容器来托管和管理Bean的生命周期。
  3. 代理模式:Spring AOP 基于动态代理技术,通过代理对象对目标对象进行增强,实现横切关注点的模块化处理。
  4. 观察者模式:Spring的事件驱动机制基于观察者模式,通过发布-订阅模型实现不同组件之间的解耦和通信。
  5. 模板方法模式:Spring的JdbcTemplate等模板类使用了模板方法模式,将通用的业务逻辑封装在抽象类中,子类可以通过重写特定的方法来实现自己的逻辑。
  6. 策略模式:Spring的事务管理中使用了策略模式,通过配置不同的事务管理策略来适应不同的事务需求。
  7. 装饰器模式:Spring的装饰模式被应用在AOP中,通过动态代理和装饰器模式实现对目标对象的增强

设计模式的单例和Bean单例有什么区别

单例模式主要作用是为了让Java应用程序中,Class有且仅有一个,它的好处是可以避免不必要的重复操作,比如数据库连接,或者工具的初始化等,Spring资源管理器常将一些资源管理器设计为单例模式。

区别

运行环境不一样:设计模式运行在Java程序中,而Bean运行在容器中,一个程序可以有很多个容器,但是一个程序只能有一个JVM,如果

Spring中的单例Bean是线程安全的么

spring只是帮我们创建和管理bean,并不能保证线程安全,如果bean中存在成员变量不能被修改(无状态)是安全的,如果成员变量能被修改(有状态)这个时候不安全,可以使用线程安全的方法处理,如原子类和Threadlocal的方法保证线程安全

为了确保单例Bean的线程安全性,可以采取以下几种方式:

  1. 避免在单例Bean中使用可变的实例变量,或者确保对这些变量的访问是线程安全的,例如使用同步机制(如synchronized关键字)或使用线程安全的数据结构。
  2. 尽量避免在单例Bean中使用共享的外部资源,如数据库连接、文件等。如果必须使用共享资源,需要确保对这些资源的访问是线程安全的(如使用ThreadLocal等)来保证线程安全。
  3. 使用无状态的单例Bean。无状态的单例Bean不包含任何实例变量,只包含方法和局部变量,因此不会有线程安全问题。
  4. 采用

Spring的事务隔离级别

总体来说跟数据库的一致,只是多了一个默认

  1. DEFAULT(默认):使用数据库默认的事务隔离级别。通常为数据库的默认隔离级别,如Oracle为READ COMMITTED,MySQL为REPEATABLE READ。
  2. READ_UNCOMMITTED:最低的隔离级别,允许读取未提交的数据。事务可以读取其他事务未提交的数据,可能会导致脏读、不可重复读和幻读的问题。
  3. READ_COMMITTED:保证一个事务只能读取到已提交的数据。事务读取的数据是其他事务已经提交的数据,避免了脏读的问题。但可能会出现不可重复读和幻读的问题。
  4. REPEATABLE_READ:保证一个事务在同一个查询中多次读取的数据是一致的。事务期间,其他事务对数据的修改不可见,避免了脏读和不可重复读的问题。但可能会出现幻读的问题。
  5. SERIALIZABLE:最高的隔离级别,保证事务串行执行,避免了脏读、不可重复读和幻读的问题。但会降低并发性能,因为事务需要串行执行。

通过@Transactional注解的isolation属性来指定事务隔离级别

@Transactional(readOnly=true) 真的是提高性能的灵丹妙药吗?

  1. 通过执行 SET TRANSACTION READ ONLY,将当前事务设置为只读事务。这意味着在此事务内部,任何修改数据的操作(如 INSERTUPDATEDELETE)都将被禁止,只能执行读取操作(如 SELECT)。
  2. 只读事务依然会运用上隔离级别(MVCC),需要事务隔离级别需要一定性能开销。

如果应用需要保证数据的一致性和隔离性,那么开启只读事务是必要的;如果不需要这些保证,并且追求查询操作的性能优化,那么不开启事务可能更为合适。

Spring的事务传播机制

  1. REQUIRED:如果当前存在事务,则加入该事务,如果当前没有事务,则创建一个新的事务。这是最常用的传播行为,也是默认的,适用于大多数情况。
  2. REQUIRES_NEW:无论当前是否存在事务,都创建一个新的事务。如果当前存在事务,则将当前事务挂起。适用于需要独立事务执行的场景,不受外部事务的影响。
  3. SUPPORTS:如果当前存在事务,则加入该事务,如果当前没有事务,则以非事务方式执行。适用于不需要强制事务的场景,可以与其他事务方法共享事务。
  4. NOT_SUPPORTED:以非事务方式执行,如果当前存在事务,则将当前事务挂起。适用于不需要事务支持的场景,可以在方法执行期间暂时禁用事务。
  5. MANDATORY:如果当前存在事务,则加入该事务,如果当前没有事务,则抛出异常。适用于必须在事务中执行的场景,如果没有事务则会抛出异常。
  6. NESTED:如果当前存在事务,则在嵌套事务中执行,如果当前没有事务,则创建一个新的事务。嵌套事务是外部事务的一部分,可以独立提交或回滚。适用于需要在嵌套事务中执行的场景。
  7. NEVER:以非事务方式执行,如果当前存在事务,则抛出异常。适用于不允许在事务中执行的场景,如果存在事务则会抛出异常。

通过@Transactional注解的propagation属性来指定事务传播行为 。

Spring AOP和 AspectJ AOP

是两种不同的 AOP 实现方式,它们在实现上有一些区别。下面是它们之间的主要区别:

  1. 基于代理 vs 字节码增强:
    • Spring AOP: Spring AOP 是基于代理的 AOP 实现。它利用动态代理技术(JDK 动态代理和 CGLIB)来实现 AOP 横切逻辑的织入。对于基于接口的目标类,Spring 使用 JDK 动态代理;对于没有实现接口的目标类,Spring 使用 CGLIB 生成子类来实现代理。
    • AspectJ AOP: AspectJ AOP 是基于字节码增强的 AOP 实现。它通过在编译期或者类加载期修改目标类的字节码来实现 AOP 横切逻辑的织入。AspectJ 提供了更强大和灵活的 AOP 功能,可以进行更细粒度的控制和切入。
  2. 织入时机:
    • Spring AOP: Spring AOP 在运行时动态地将切面织入到目标类中。因为使用代理,Spring AOP 只能对 Spring 管理的 Bean 进行 AOP 操作,且只能针对 Spring AOP 支持的切点表达式进行织入。
    • AspectJ AOP: AspectJ AOP 可以在编译期或者类加载期静态地将切面织入到目标类中,也可以在运行时动态织入。AspectJ 提供了更多的织入时机和灵活性,可以对任意的 Java 类进行 AOP 操作,并支持更强大的切入点表达式。
  3. 性能:
    • Spring AOP: Spring AOP 的性能相对较高,因为它基于代理,对目标类的影响比较小。但是,Spring AOP 对于复杂的切面和大规模的系统可能会有一定的性能影响。
    • AspectJ AOP: AspectJ AOP 的性能一般比 Spring AOP 略低,因为它对字节码进行了修改和增强,对目标类的影响更大。但是 AspectJ 提供了更强大的功能和更高的灵活性。
  4. 功能和表达式支持:
    • Spring AOP: Spring AOP 提供了一些常用的 AOP 功能,如前置通知、后置通知、环绕通知等,同时支持基于切点表达式的切入。
    • AspectJ AOP: AspectJ 提供了更丰富的 AOP 功能,如引入(introduction)、静态初始化块织入等,并且支持更强大的切点表达式和切面定义方式。
      综上所述,Spring AOP 和 AspectJ AOP 在实现方式、织入时机、性能和功能支持等方面有一定的区别。选择合适的 AOP 实现方式取决于项目的需求和复杂度。如果需要更强大的功能和更高的灵活性,可以考虑使用 AspectJ AOP;如果对性能要求较高,且功能需求较简单,则可以使用 Spring AOP。在实际项目中,也可以结合两者使用,根据需求灵活选择。

Spring自动装配Bean的方式

  1. ByName 按名字自动装配
  2. ByType 按类型自动装配
  3. 构造器装配
  4. @Autowired 注解,使用@Order或者使用@Qualifier注解去提高优先级或指定实现类

拦截器和过滤器的区别

  1. 拦截器是基于Spring的,过滤器是基于Servlet的

  2. 拦截器拦截的是Action路径(dispatcher Servlet 配置的)下的请求,过滤器几乎可以拦截所有的请求

  3. 拦截器可以访问容器中的Bean , 而过滤器不可以,但是如果过滤器是基于Spring注入的也可以访问

image-20240422210411797

Spring事件监听的核心机制是什么?

观察者模式: 它允许一个对象(称为主题或被观察者)维护一组依赖于它的对象(称为观察者),并在主题状态发生变化时通知观察者。

它包含三个核心:

  1. 事件: 事件是观察者模式中的主题状态变化的具体表示,它封装了事件发生时的信息。在Spring中,事件通常是普通的Java对象,用于传递数据或上下文信息。
  2. 事件发布者: 在Spring中,事件发布者充当主题的角色,负责触发并发布事件。它通常实现了ApplicationEventPublisher接口或使用注解@Autowired来获得事件发布功能。
  3. 事件监听器: 事件监听器充当观察者的角色,负责监听并响应事件的发生。它实现了ApplicationListener接口,通过onApplicationEvent()方法来处理事件。

Spring事务的失效原因?

  1. 方法是private也会失效,解决:改成public: Spring的事务代理通常是通过Java动态代理或CGLIB动态代理生成的,这些代理要求目标方法是公开可访问的(public)。私有方法无法被代理,因此事务将无效。解决方法是将目标方法改为public或protected。
  2. 目标类没有配置为Bean也会失效,解决:配置为Bean: Spring的事务管理需要在Spring容器中配置的Bean上才能生效。如果目标类没有被配置为Spring Bean,那么事务将无法被应用。解决方法是确保目标类被正确配置为Spring Bean。
  3. 自己捕获了异常,解决:不要捕获处理: Spring事务管理通常依赖于抛出未捕获的运行时异常来触发事务回滚。如果您在方法内部捕获了异常并处理了它,事务将不会回滚。解决方法是让异常在方法内部被抛出,以触发事务回滚。
  4. 使用CGLIB动态代理,但@Transactional声明在接口上: 默认情况下,Spring的事务代理使用基于接口的JDK动态代理。如果您将**@Transactional注解声明在接口上,而目标类是使用CGLIB代理的,事务将不会生效。解决方法是将@Transactional**注解移到目标类的方法上,或者配置Spring以使用CGLIB代理接口。
  5. 跨越多个线程的事务管理,解决:使用编程式事务或分布式事务: 如果您的应用程序在多个线程之间共享数据库连接和事务上下文,事务可能会失效,除非适当地配置事务传播属性。
  6. 事务传播属性或捕获异常等设置不正确: 事务传播属性定义了事务如何传播到嵌套方法或外部方法。如果事务传播属性设置不正确,可能会导致事务失效或不符合预期的行为。

SpringBoot的启动原理?

  1. 运行Main方法: 应用程序启动始于Main方法的执行。在Main方法中,创建了一个SpringApplication实例,用于引导应用程序的启动。同时,SpringApplication会根据spring.factories文件加载并注册监听器、ApplicationContextInitializer等扩展接口实现。
  2. 运行run方法: 运行SpringApplication的run方法是应用程序启动的入口。在这一步,Spring Boot会 启动Spring进而创建内置tomcat,进去run方法后还做了很多其他事:
  3. Spring Boot会读取和解析环境变量、配置文件(如application.properties或application.yml)等,以获取应用程序的配置信息。
  4. 之后再创建ApplicationContext也就是我们熟知的Spring上下文: 在这一步,Spring Boot会根据应用程序的类型(例如,Web应用程序)创建相应的ApplicationContext。对于Web应用程序,通常创建的是ServletWebServerApplicationContext。
  5. 预初始化上下文: Spring Boot会将启动类作为配置类,读取并注册为BeanDefinition,这使得Spring容器可以识别应用程序的配置
  6. 调用refresh: 此时,Spring Boot调用了refresh方法来加载和初始化Spring容器。在这一过程中,会执行一系列操作,包括解析@Import注解以加载自动配置类,创建和注册BeanDefinition等。
  7. 创建内置servlet容器: 如果应用程序是一个Web应用程序,Spring Boot会在这一步创建内置的servlet容器(例如Tomcat),以便应用程序可以接受HTTP请求。这个容器将被Spring Boot自动配置,并且可以通过配置进行自定义。
  8. 监听器和扩展点: 在整个启动过程中,Spring Boot会调用各种监听器和扩展点,这些组件可以用来对应用程序进行扩展和定制。例如,您可以使用监听器来处理应用程序启动和关闭事件,或者使用ApplicationContextInitializer来自定义ApplicationContext的初始化。

分布式事务详解

分布式事务五种方案及两个流行框架 - 螺旋自嘲 - 博客园 (cnblogs.com)

2PC

2PC(Two-phase commit protocol),中文叫二阶段提交。二阶段提交是一种强一致性设计,2PC 引入一个事务协调者的角色来协调管理各参与者(也可称之为各本地资源)的提交和回滚,二阶段分别指的是准备(投票)和提交两个阶段。

当第一阶段参与者都准备成功了,协调者就会发送提交事务的请求。反之如果有一个参与者准备失败则发送回滚事物的请求

img

img

2PC是一个同步阻塞协议,只有第一阶段所有参与者都响应了,才会执行第二阶段。在第一阶段中,协调者有超时机制,当因为网络问题或者参与者执行超时和参与者不在线的情况,协调者会向所有参与者发送回滚命令。但是第二阶段是没有超时的,只能不断地重试提交或回滚

2PC 是一种尽量保证强一致性的分布式事务,因此它是同步阻塞的,而同步阻塞就导致长久的资源锁定问题,总体而言效率低,并且存在单点故障问题,在极端条件下存在数据不一致的风险

3PC

3PC相比于2PC多了一个预提交阶段的步骤,准备阶段预提交阶段提交阶段

预提交是把2PC的提交阶段拆成两次去做,相应的性能会差一点,而且绝大部分情况下资源应该都是可用的,等同于明知故问。2PC有的问题3PC也有存在,所以3PC应用的很少,不展开讨论了。

TCC

TCC 指的是Try - Confirm - Cancel

  • Try 指的是预留,即资源的预留和锁定。
  • Confirm 指的是确认操作,这一步其实就是真正的执行了。
  • Cancel 指的是撤销操作,可以理解为把预留阶段的动作撤销了。

一个分布式的全局事务,整体是 两阶段提交 的模型。TCC也是一样的,单相对应2PC和3PC来说,把事务管理从数据库层面,提取到了业务层面

TCC第一阶段:try行为,试探性操作

TCC第二阶段:confirm或cancel操作,第一阶段成功就会调用confirm,失败就会cancel操作

TCC还需要一个全局事务管理者的角色,用来记录TCC全局事务状态并提交或回滚事务

img

由于TCC每一步操作都需要业务上的定义,对于一个操作都要写三个方法对应try、confirm、cancel。

因此TCC对业务的侵入性比较大和业务是紧耦合的关系。

但是因为TCC是业务上的实现,所以他的适用范围更广,可以跨数据库、跨不同的业务系统来实现事务。

事务控制代码都需要开发去写,所以需要做好异常控制:

  1. 空回滚允许

    现象是try没有被执行,就调用了cancel。

    出现原因:

    • Try超时(丢包)
    • 分布式事务回滚,触发cancel
    • 未收到try,收到cancel

    解决办法:让cancel能够识别出这是一个空回滚,可以记录事务执行状态,cancel中判断try是否执行了。

  2. 幂等控制

    事务协调着会重复调用,try、confirm、cancel三个方法都需要实现幂等控制

    解决办法:记录事务执行状态,如果执行过了,就不再执行。

  3. 防悬挂控制

    Cancel比Try先执行

    出现原因:

    • Try超时(拥堵)
    • 分布式事务回滚,出发cancel
    • 拥堵的Try到达

    解决办法:记录事务执行状态,try执行时判断cancel是否执行了。

  4. 并发控制

优点

  1. 可靠性高
  2. 实时性高

缺点

  1. 开发复杂度高
  2. 因为事务状态管理,需要多次DB操作,性能有一定损耗

本地消息列表

此方案的核心是将需要分布式处理的任务通过消息日志的方式来异步执行。消息日志可以存储到本地文本、数据库或消息队列,再通过业务规则自动或人工发起重试。人工重试更多的是应用于支付场景,通过对账系统对事后问题的处理。

消息事务

如果说本地消息表方案是消息+本地表实现的消息的可靠性和事务的,那消息事务方案就是通过消息中间件本身的事务体系,解决了本地事务表对业务的耦合和定时任务扫描的痛点。

  • 事务消息:消息队列RocketMQ版提供类似XA或Open XA的分布式事务功能,通过消息队列RocketMQ版事务消息能达到分布式事务的最终一致。
  • 半事务消息:暂不能投递的消息,发送方已经成功地将消息发送到了消息队列RocketMQ版服务端,但是服务端未收到生产者对该消息的二次确认,此时该消息被标记成“暂不能投递”状态,处于该种状态下的消息即半事务消息。
  • 消息回查:由于网络闪断、生产者应用重启等原因,导致某条事务消息的二次确认丢失,消息队列RocketMQ版服务端通过扫描发现某条消息长期处于“半事务消息”时,需要主动向消息生产者询问该消息的最终状态(Commit或是Rollback),该询问过程即消息回查。

Seata事务框架

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/657834.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【前端篇】前端开发大厂面试真题

为助力小伙伴们梳理前端知识体系,从而能够充分地做好面试准备,那么今天就来给大家分享一份前端开发的面试真题与相关知识点,其中涵盖了最新版本的八股文(包含最新的 Vue 3 面试题)、高频算法题以及大佬的面经&#xff…

delphi advstringgrid 表格中加checkbox

加checkbox for i : 0 to sg.RowCount - 1 dobeginsg.AddCheckBox(1,i,false,false);for j : 0 to sg.ColCount - 1 dobeginif j <> 1 thensg.CellProperties[j,i].ReadOnly : true;//只读end;end; 读取&#xff0c;设置checkbox&#xff0c;全选&#xff0c;反选 proced…

6月来得及!考研数学120分复习规划:660/880/1000/1800怎么刷?

首先&#xff0c;120分是个什么概念&#xff1f; 如果目标120&#xff0c;历年真题就要135以上。这是因为&#xff1a; 1. 习题册里都是历年真题改编&#xff0c;很多题型见过了&#xff1b; 2. 考场发挥有不确定因素&#xff0c;所以需要安全边界。 总体规划 那么&#xff…

【设计模式深度剖析】【6】【结构型】【外观模式】| 以电脑开关按钮为例,并结合微服务架构的API网关加深理解

&#x1f448;️上一篇:桥接模式 设计模式-专栏&#x1f448;️ 目 录 外观模式&#xff08;Facade Pattern&#xff09;定义英文原文直译如何理解呢&#xff1f;字面理解代码实现中的理解生活案例&#xff1a;操作多功能料理机典型案例分析&#xff1a;API网关与外观模式 外…

【蓝桥杯】第十四届蓝桥杯大赛软件赛国赛C/C++ 大学 B 组

答题结果页 - 蓝桥云课 (lanqiao.cn) 0子2023 - 蓝桥云课 (lanqiao.cn)&#xff08;暴力枚举 #include<bits/stdc.h> using lllong long; using ullunsigned long long; #define fir first #define sec second //#define int llconst int N1e510; const int mod1e97;int…

多线程新手村4--定时器

定时器是日常开发中很常见的组件&#xff0c;定时器大家可能不知道是干什么的&#xff0c;但是定时炸弹肯定都听过&#xff0c;定个时间&#xff0c;过一段时间后bomb&#xff01;&#xff01;&#xff01;爆炸 定时器的逻辑和这个一样&#xff0c;约定一个时间&#xff0c;这…

windows ollama 指定模型下载路径

为Ollama指定模型的下载路径 在Windows系统中&#xff0c;如果想为Ollama指定模型的下载路径&#xff0c;可以通过设置环境变量来实现。以下是详细的步骤&#xff1a; 确定默认下载路径&#xff1a; 默认情况下&#xff0c;Ollama的模型可能会下载到C:\Users\<用户名>…

类别型特征

#机器学习 #深度学习 #基础知识 #特征工程 #数据编码 背景 在现实生活中,我们面对的数据类型有很多,其中有的数据天然为数值类型具备数值意义,那么可以很自然地和算法结合,但是大部分数据他没有天然的数值意义,那么将他们送入到算法前,就需要对数据进行编码处理,将其转换为数…

如何成为快手外卖代理?本地生活服务平台加盟条件解析

近年来&#xff0c;以抖音、快手和小红书等为代表的互联网大厂纷纷进军本地生活领域&#xff0c;改变美团和饿了么二分天下的这一局面的同时&#xff0c;也让本地生活成为了众多创业者眼中的“香饽饽”。其中&#xff0c;快手凭借着其庞大的用户群体&#xff0c;让快手团购外卖…

js使用链表实现音乐播放器(新增,下一首播放,置顶,删除)

什么是链表 链表是一种线性数据结构&#xff0c;与数组类似&#xff0c;它用于存储一系列元素。不过&#xff0c;与数组在内存中连续存储元素不同&#xff0c;链表中的元素&#xff08;称为节点&#xff09;在内存中可以是非连续存放的。每个节点包含两部分&#xff1a;一部分…

利用CNN和迁移学习检测太阳能电池板上的尘埃

太阳能电池板已经成为农业、交通、建筑和酒店等多个行业中受欢迎的可再生能源来源。通过利用太阳的能量&#xff0c;我们可以在不损害环境的情况下产生电力。然而&#xff0c;使用太阳能电池板面临着一些挑战&#xff0c;其中最大的之一是它们表面上尘埃的积累。这会显著降低它…

【机器学习】MS_MARCO_Web_Search解析说明

MS MARCO Web Search&#xff1a;引领大型模型与信息检索的新纪元 一、引言&#xff1a;大型模型与信息检索的挑战二、MS MARCO Web Search数据集的特点三、MS MARCO Web Search数据集的应用五、结语 在信息爆炸的时代&#xff0c;如何高效、准确地从海量数据中检索出有价值的信…

Java SE基础知识(13)

知识梳理&#xff1a; package LocalDate;import java.time.DayOfWeek; import java.time.LocalDate; import java.time.Month; import java.time.MonthDay; import java.util.Locale;public class demo1 {public static void main(String[] args) {//1.获取当前时间的日历对象…

构建php环境、安装、依赖、nginx配置、ab压力测试命令、添加php-fpm为系统服务

目录 php简介 官网php安装包 选择下载稳定版本 &#xff08;建议使用此版本&#xff0c;文章以此版本为例&#xff09; 安装php解析环境 准备工作 安装依赖 zlib-devel 和 libxml2-devel包。 安装扩展工具库 安装 libmcrypt 安装 mhash 安装mcrypt 安装php 选项含…

VBA技术资料MF158:获取系统的用户名

我给VBA的定义&#xff1a;VBA是个人小型自动化处理的有效工具。利用好了&#xff0c;可以大大提高自己的工作效率&#xff0c;而且可以提高数据的准确度。“VBA语言専攻”提供的教程一共九套&#xff0c;分为初级、中级、高级三大部分&#xff0c;教程是对VBA的系统讲解&#…

GBB和Prob IoU[旋转目标检测理论篇]

在开始介绍YOLOv8_obb网络之前,需要先介绍一下arxiv.org/pdf/2106.06072 这篇文章的工作,因为v8_obb就是基于这篇论文提出的GBB和prob IoU来实现旋转目标检测的。 1.高斯分布 一维高斯分布的规律是中间高两边低,且当x为均值的时候取到最大值,表达式如下,标准正态分布图如…

加密资产私钥安全完整手册(一) ,bitget钱包为例

比特币和以太坊等加密货币的兴起开创了数字金融的新时代&#xff0c;但也带来了独特的安全挑战。这些代表现实世界价值的数字资产已成为黑客和窃贼的主要目标。为了安全地应对这种情况&#xff0c;了解私钥的基本概念至关重要。 私钥是加密货币所有权和安全性的基石。它们相当于…

基于图卷积网络的人体3D网格分割

深度学习在 2D 视觉识别任务上取得了巨大成功。十年前被认为极其困难的图像分类和分割等任务&#xff0c;现在可以通过具有类似人类性能的神经网络来解决。这一成功归功于卷积神经网络 (CNN)&#xff0c;它取代了手工制作的描述符。 NSDT工具推荐&#xff1a; Three.js AI纹理开…

阿里云和AWS的CDN产品对比分析

在现代互联网时代,内容分发网络(CDN)已成为确保网站和应用程序高性能和可用性的关键基础设施。作为两家领先的云服务提供商,阿里云和Amazon Web Services(AWS)都提供了成熟的CDN解决方案,帮助企业优化网络传输和提升用户体验。我们九河云一直致力于阿里云和AWS云相关业务&#…

【全开源】西陆家政系统源码小程序(FastAdmin+ThinkPHP+原生微信小程序)

打造高效便捷的家政服务平台 一、引言&#xff1a;家政服务的数字化转型 随着人们生活节奏的加快&#xff0c;家政服务需求日益增长。为了满足广大用户对高效、便捷的家政服务的需求&#xff0c;家政小程序系统源码应运而生。这款源码不仅能够帮助家政服务提供商快速搭建自己…