Java面试——Spring系列总结

文章目录:

1.什么是Spring?

2.Spring由哪些模块组成?

3.Spring中都用到了哪些设计模式?

4.什么是Spring IOC容器?有什么作用?

5.Spring IoC的实现机制

6.BeanFactory 和 ApplicationContext有什么区别?

7.什么是Spring的依赖注入(Dependency Injection)?

8.什么是Spring AOP?

9.Spring AOP 与 AspectJ AOP 有什么区别?AOP 有哪些实现方式?

10.解释一下Spring AOP里面的几个名词

11.Spring AOP中的通知有哪些类型?

12.Spring支持的几种bean的作用域

13.解释一下Spring中bean的生命周期

14.Spring支持的事务管理类型, Spring事务实现方式有哪些?你更倾向用哪种事务管理类型?

15.什么是Spring事务的传播行为?

16.什么是Spring事务的隔离级别?


1.什么是Spring?

Spring是一个轻量级Java开源框架,最早由Rod Johnson创建,目的是解决企业级应用开发的复杂性,简化Java开发。Spring为开发Java应用程序提供全面的基础架构支持,因此Java开发者可以专注于应用程序的开发。

Spring可以做很多事情,它为企业级开发提供给了丰富的功能,但是这些功能的底层都依赖于它的两个核心特性,也就是控制反转(IoC)也可以说依赖注入(DI)面向切面编程(AOP)

为了降低Java开发的复杂性,Spring采取了以下4种关键策略

  • 基于POJO的轻量级和最小侵入性编程;
  • 通过依赖注入和面向接口实现松耦合;
  • 基于切面和惯例进行声明式编程;
  • 通过切面和模板减少样板式代码。

Spring设计目标:Spring为开发者提供一个一站式轻量级应用开发平台;

Spring设计理念:在JavaEE开发中,支持POJO和JavaBean开发方式,使应用面向接口开发,充分支持OO(面向对象)设计方法;Spring通过IoC容器实现对象耦合关系的管理,并实现依赖反转,将对象之间的依赖关系交给IoC容器,实现解耦;

Spring框架的核心:IoC容器和AOP模块。通过IoC容器管理POJO对象以及他们之间的耦合关系;通过AOP以动态非侵入的方式增强服务,把遍布于应用各层的功能分离出来形成可重用的功能组件。

2.Spring由哪些模块组成?

img

  • spring core:提供了框架的基本组成部分,包括控制反转(Inversion of Control,IOC)和依赖注入(Dependency Injection,DI)功能。
  • spring beans:提供了BeanFactory,是工厂模式的一个经典实现,Spring将管理对象称为Bean。
  • spring context:构建于 core 封装包基础上的 context 封装包,提供了一种框架式的对象访问方法。
  • spring jdbc:提供了一个JDBC的抽象层,消除了烦琐的JDBC编码和数据库厂商特有的错误代码解析, 用于简化JDBC。
  • spring aop:提供了面向切面的编程实现,让你可以自定义拦截器、切点等。
  • spring Web:提供了针对 Web 开发的集成特性,例如文件上传,利用 servlet listeners 进行 ioc 容器初始化和针对 Web 的 ApplicationContext。
  • spring test:主要为测试提供支持的,支持使用JUnit或TestNG对Spring组件进行单元测试和集成测试。

3.Spring中都用到了哪些设计模式?

  1. 工厂模式:BeanFactory就是简单工厂模式的体现,用来创建对象的实例;
  2. 单例模式:Bean默认为单例模式。
  3. 代理模式:Spring的AOP功能用到了JDK的动态代理和CGLIB字节码生成技术;
  4. 模板方法:用来解决代码重复的问题。比如:RestTemplate, JmsTemplate, JpaTemplate。
  5. 观察者模式:定义对象间一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都会得到通知被动更新,如Spring中listener的实现–ApplicationListener。

4.什么是Spring IOC容器?有什么作用?

控制反转即IoC (Inversion of Control),它把传统上由程序代码直接操控的对象的调用权交给容器,通过容器来实现对象组件的装配和管理。所谓的“控制反转”概念就是对对象组件控制权的转移,从程序代码本身转移到了外部容器。

Spring IOC 负责创建对象,管理对象(通过依赖注入(DI),装配对象,配置对象,并且管理这些对象的整个生命周期。)

IoC容器的作用:

  • 管理对象的创建和依赖关系的维护。对象的创建并不是一件简单的事,在对象关系比较复杂时,如果依赖关系需要程序猿来维护的话,那是相当头疼的
  • 解耦,由容器去维护具体的对象
  • 托管了类的整个生命周期,比如我们需要在类的产生过程中做一些处理,最直接的例子就是代理,如果有容器程序可以把这部分处理交给容器,应用程序则无需去关心类是如何完成代理的

5.Spring IoC的实现机制

Spring 中的 IoC 的实现原理就是工厂模式加反射机制。

package com.szh.spring;/****/
interface Fruit {void eat();
}class Apple implements Fruit {public Apple() {System.out.println("Apple类的无参构造执行了....");}@Overridepublic void eat() {System.out.println("苹果");}
}class Banana implements Fruit {public Banana() {System.out.println("Banana类的无参构造执行了....");}@Overridepublic void eat() {System.out.println("香蕉");}
}class Factory {public static Fruit getInstance(String className) {Fruit fruit = null;try {fruit = (Fruit) Class.forName(className).newInstance();} catch (Exception e) {e.printStackTrace();}return fruit;}
}public class Client {public static void main(String[] args) {Fruit fruit = Factory.getInstance("com.szh.spring.Apple");if (fruit != null) {fruit.eat();}}
}

img

6.BeanFactory 和 ApplicationContext有什么区别?

BeanFactory和ApplicationContext是Spring的两大核心接口,都可以当做Spring的容器。其中ApplicationContext是BeanFactory的子接口。

依赖关系

BeanFactory:是Spring里面最底层的接口,包含了各种Bean的定义,读取bean配置文档,管理bean的加载、实例化,控制bean的生命周期,维护bean之间的依赖关系。我们可以称之为 “低级容器”

ApplicationContext接口作为BeanFactory的派生,可以称之为 “高级容器”。除了提供BeanFactory所具有的功能外,还提供了更完整的框架功能:

  • 继承MessageSource,因此支持国际化。
  • 统一的资源文件访问方式。
  • 提供在监听器中注册bean的事件。
  • 同时加载多个配置文件。
  • 载入多个(有继承关系)上下文 ,使得每一个上下文都专注于一个特定的层次,比如应用的web层。

加载方式

BeanFactroy采用的是延迟加载形式来注入Bean的,即只有在使用到某个Bean时(调用getBean()),才对该Bean进行加载实例化。这样,我们就不能发现一些存在的Spring的配置问题。如果Bean的某一个属性没有注入,BeanFacotry加载后,直至第一次使用调用getBean方法才会抛出异常。

ApplicationContext,它是在容器启动时,一次性创建了所有的Bean。这样,在容器启动时,我们就可以发现Spring中存在的配置错误,这样有利于检查所依赖属性是否注入。ApplicationContext启动后预载入所有的单实例Bean,通过预载入单实例bean,确保当你需要的时候,你就不用等待,因为它们已经创建好了。

相对于基本的BeanFactory,ApplicationContext 唯一的不足是占用内存空间。当应用程序配置Bean较多时,程序启动较慢。

创建方式

BeanFactory通常以编程的方式被创建,ApplicationContext还能以声明的方式创建,如使用ContextLoader。

注册方式

BeanFactory和ApplicationContext都支持BeanPostProcessor、BeanFactoryPostProcessor的使用,但两者之间的区别是:BeanFactory需要手动注册,而ApplicationContext则是自动注册。

7.什么是Spring的依赖注入(Dependency Injection)?

依赖注入:相对于IoC而言,依赖注入(DI)更加准确地描述了IoC的设计理念。所谓依赖注入(Dependency Injection),即组件之间的依赖关系由容器在应用系统运行期来决定,也就是由容器动态地将某种依赖关系的目标对象实例注入到应用系统中的各个关联的组件之中。组件不做定位查询,只提供普通的Java方法,让容器去决定依赖关系。

依赖注入是时下最流行的IoC实现方式,依赖注入分为接口注入(Interface Injection),Setter方法注入(Setter Injection)和构造器注入(Constructor Injection)三种方式。其中接口注入由于在灵活性和易用性比较差,现在从Spring4开始已被废弃。

构造器注入:构造器注入是容器通过调用一个类的构造器来实现的,该构造器有一系列参数,每个参数都必须注入。

Setter方法注入:Setter方法注入是容器通过调用无参构造器或无参static工厂方法实例化bean之后,调用该bean的setter方法来实现的依赖注入。

img

8.什么是Spring AOP?

AOP(Aspect-Oriented Programming),一般称为面向切面编程,作为面向对象的一种补充,用于将那些与业务无关,但却对多个对象产生影响的公共行为和逻辑,抽取并封装为一个可重用的模块,这个模块被命名为“切面”(Aspect),通过面向切面编程减少了系统中的重复代码,降低了模块间的耦合度,同时提高了系统的可维护性。常用于权限认证、日志、事务处理等。

9.Spring AOP 与 AspectJ AOP 有什么区别?AOP 有哪些实现方式?

AOP实现的关键在于代理模式,AOP代理主要分为静态代理和动态代理。静态代理的代表为AspectJ;动态代理则以Spring AOP为代表。

(1)AspectJ是静态代理的增强,所谓静态代理,就是AOP框架会在编译阶段生成AOP代理类,因此也称为编译时增强,他会在编译阶段将AspectJ(切面)织入到Java字节码中,运行的时候就是增强之后的AOP对象。

(2)Spring AOP使用的动态代理,所谓的动态代理就是说AOP框架不会去修改字节码,而是每次运行时在内存中临时为方法生成一个AOP对象,这个AOP对象包含了目标对象的全部方法,并且在特定的切点做了增强处理,并回调原对象的方法。

10.解释一下Spring AOP里面的几个名词

img

  1. Aspect:切面,给业务方法增加到功能。切面泛指交叉业务逻辑。常用的切面是通知(Advice)。实际就是对主业务逻辑的一种增强。
  2. JoinPoint:连接点,连接切面的业务方法。连接点指可以被切面织入的具体方法。通常业务接口中的方法均为连接点。
  3. Pointcut:切入点,切入点指声明的一个或多个连接点的集合。通过切入点指定一组方法。被标记为 final 的方法是不能作为连接点与切入点的。因为最终的是不能被修改的,不能被增强的。
  4. Target:目标对象,目标对象指将要被增强的对象。即包含主业务逻辑的类的对象。
  5. Advice:通知,通知表示切面的执行时间,Advice 也叫增强。换个角度来说,通知定义了增强代码切入到目标代码的时间点,是目标方法执行之前执行,还是之后执行等。通知类型不同,切入时间不同。

切入点定义切入的位置,通知定义切入的时间。

11.Spring AOP中的通知有哪些类型?

通知类型说明使用场景
前置通知(Before)在目标方法被执行之前调用通知
后置通知(After)无论如何都会在目标方法执行之后调用通知记录日志(方法已经调用,但不一定成功)
最终通知(After-returning )无论目标方法是否抛出异常,该增强均会被执行。记录日志(方法已经成功调用)
异常通知(After-throwing)在目标方法抛出异常后调用通知异常处理
环绕通知(Around)通知包裹了目标方法,在目标方法调用之前和调用之后执行自定义的行为事务权限控制

12.Spring支持的几种bean的作用域

当定义一个bean在Spring里,我们还能给这个bean声明一个作用域。它可以通过bean的scope属性来定义。

Spring框架支持以下五种bean的作用域:

作用域描述
singleton单例模式,在spring IoC容器仅存在一个Bean实例,默认值
prototype原型模式,每次从容器中获取Bean时,都返回一个新的实例,即每次调用getBean()时,相当于执行newXxxBean()
request每次HTTP请求都会创建一个新的Bean,该作用域仅在基于web的Spring ApplicationContext环境下有效
session同一个HTTP Session共享一个Bean,不同Session使用不同的Bean,该作用域仅在基于web的Spring ApplicationContext环境下有效
global-session同一个全局的HTTP Session中共享一个Bean,一般用于Portlet应用环境,该作用域仅在基于web的Spring ApplicationContext环境下有效

因为经常用到的就是前两种 singleton、prototype,所以下面通过简单的代码案例演示一下。

首先演示当Spring Bean的作用域设置为 默认singleton 的情况。依次是实体类、Spring配置文件、测试方法。

package com.szh.spring;/*** */
public class Book {private String bookName;private String bookAuthor;public void setBookName(String bookName) {this.bookName = bookName;}public void setBookAuthor(String bookAuthor) {this.bookAuthor = bookAuthor;}@Overridepublic String toString() {return "Book{" +"bookName='" + bookName + '\'' +", bookAuthor='" + bookAuthor + '\'' +'}';}
}
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><bean id="book" class="com.szh.spring.Book" scope="singleton"><property name="bookName" value="盗墓笔记"/><property name="bookAuthor" value="南派三叔"/></bean></beans>
    @Testpublic void testBook() {ApplicationContext context =new ClassPathXmlApplicationContext("bean1.xml");Book book1 = context.getBean("book",Book.class);Book book2 = context.getBean("book",Book.class);System.out.println(book1);System.out.println(book2);System.out.println(book1 == book2);}

img

从上面的输出结果中可以看到,在bean的作用域为 singleton 单例的情况下,通过Spring IoC容器依次拿到的这两个对象是一样的,也就是说此时容器中仅存在这一个bean(Book)。

下面再来演示 bean 作用域为prototype的情况。所有测试代码和上面的一样,只是将配置文件中 标签中的 scope 属性修改为 prototype。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><bean id="book" class="com.szh.spring.Book" scope="prototype"><property name="bookName" value="盗墓笔记"/><property name="bookAuthor" value="南派三叔"/></bean></beans>

img

这个时候,我们可以看到从容器中拿到的这两个对象就不一样了,因为此时bean的作用域变成了 prototype 多实例情况,也就是说容器中可以有多个Book实例。

关于 singleton 和 prototype 的区别:

  1. singleton 单实例,prototype 多实例。
  2. 设置 scope 值是 singleton 的时候,加载 spring 配置文件时就会创建单实例对象。
    设置 scope 值是 prototype 的时候,不是在加载 spring 配置文件的时候创建 对象,而是在调用getBean 方法时候创建多实例对象。

13.解释一下Spring中bean的生命周期

在传统的Java应用中,bean的生命周期很简单。使用Java关键字new进行bean实例化,然后该bean就可以使用了。一旦该bean不再被使用,则由Java自动进行垃圾回收。相比之下,Spring容器中的bean的生命周期就显得相对复杂多了。正确理解Spring bean的生命周期非常重要,因为你或许要利用Spring提供的扩展点来自定义bean的创建过程。

下图展示了bean装载到Spring应用上下文中的一个典型的生命周期过程。

img

Spring对bean进行实例化;

Spring将值和bean的引用注入到bean对应的属性中;(set方法赋值、引用类型、构造器等等)

如果bean实现了BeanNameAware接口,Spring将bean的ID传递给setBean-Name()方法;

如果bean实现了BeanFactoryAware接口,Spring将调用setBeanFactory()方法,将BeanFactory容器实例传入;

如果bean实现了ApplicationContextAware接口,Spring将调用setApplicationContext()方法,将bean所在的应用上下文的引用传入进来;

如果bean实现了BeanPostProcessor接口,Spring将调用它们的post-ProcessBeforeInitialization()方法;

如果bean实现了InitializingBean接口,Spring将调用它们的after-PropertiesSet()方法。类似地如果bean使用initmethod声明了初始化方法,该方法也会被调用;

此时,bean已经准备就绪,可以被应用程序使用了,它们将一直驻留在应用上下文中,直到该应用上下文被销毁;

如果bean实现了DisposableBean接口,Spring将调用它的destroy()接口方法。同样,如果bean使用destroy-method声明了销毁方法,该方法也会被调用。


下面简单演示一下Spring Bean的生命周期:👇👇👇

package com.szh.spring.bean;/****/
public class Orders {private String name;public Orders() {System.out.println("第一步: 执行无参构造创建bean实例");}public void setName(String name) {this.name = name;System.out.println("第二步: 调用set方法设置属性值");}//创建执行的初始化的方法public void initMethod() {System.out.println("第三步: 执行bean初始化的方法");}//创建执行的销毁的方法public void destroyMethod() {System.out.println("第五步: 执行bean销毁的方法");}}
package com.szh.spring.bean;import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;/****/
public class MyBeanPost implements BeanPostProcessor {@Overridepublic Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {System.out.println("在初始化之前执行的方法");return bean;}@Overridepublic Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {System.out.println("在初始化之后执行的方法");return bean;}
}
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><bean id="orders" class="com.szh.spring.bean.Orders" init-method="initMethod" destroy-method="destroyMethod"><property name="name" value="手机"/></bean><!-- 配置后置处理器 --><bean id="myBeanPost" class="com.szh.spring.bean.MyBeanPost"/></beans>
    @Testpublic void testBean() {
//        ApplicationContext context =
//                new ClassPathXmlApplicationContext("bean2.xml");ClassPathXmlApplicationContext context =new ClassPathXmlApplicationContext("bean2.xml");Orders orders = context.getBean("orders",Orders.class);System.out.println("第四步: 获取创建好的bean实例对象 ---> " + orders);//手动让bean实例销毁context.close();}

img

bean 生命周期有七步

  1. 通过无参构造创建 bean 实例
  2. 为 bean 的属性设置值和对其他 bean 的引用(调用 set 方法)
  3. 把 bean 实例传递 bean 后置处理器的方法 postProcessBeforeInitialization(实现了BeanPostProcessor接口)
  4. 调用 bean 的初始化的方法(需要进行配置初始化的方法)
  5. 把 bean 实例传递 bean 后置处理器的方法 postProcessAfterInitialization(实现了BeanPostProcessor接口)
  6. bean 可以使用了(对象获取到了)
  7. 当容器关闭时候,调用 bean 的销毁的方法(需要进行配置销毁的方法)

14.Spring支持的事务管理类型, Spring事务实现方式有哪些?你更倾向用哪种事务管理类型?

Spring事务的本质其实就是数据库对事务的支持,没有数据库的事务支持,spring是无法提供事务功能的。真正的数据库层的事务提交和回滚是通过bin log或者redo log实现的。

Spring支持两种类型的事务管理:

编程式事务管理:通过编程的方式管理事务,灵活性好,但是难维护。

声明式事务管理:将业务代码和事务管理分离,只需用注解和XML配置来管理事务。

大多数情况下选择声明式事务管理,虽然比编程式事务管理少了一点灵活性,最细粒度只能作用到方法级别,无法做到像编程式事务那样可以作用到代码块级别,但是声明式事务管理对应用代码的影响最小,更符合一个无侵入的轻量级容器的思想,具有更好的可维护性。

15.什么是Spring事务的传播行为?

spring事务的传播行为说的是,当多个事务同时存在的时候,spring如何处理这些事务的行为。

  1. PROPAGATION_REQUIRED:如果当前没有事务,就创建一个新事务,如果当前存在事务,就加入该事务,该设置是最常用的设置。
  2. PROPAGATION_SUPPORTS:支持当前事务,如果当前存在事务,就加入该事务,如果当前不存在事务,就以非事务执行。
  3. PROPAGATION_MANDATORY:支持当前事务,如果当前存在事务,就加入该事务,如果当前不存在事务,就抛出异常。
  4. PROPAGATION_REQUIRES_NEW:创建新事务,无论当前存不存在事务,都创建新事务。
  5. PROPAGATION_NOT_SUPPORTED:以非事务方式执行,如果当前存在事务,就把当前事务挂起。
  6. PROPAGATION_NEVER:以非事务方式执行,如果当前存在事务,则抛出异常。
  7. PROPAGATION_NESTED:如果当前存在事务,则在嵌套事务内执行。如果当前没有事务,则按REQUIRED属性执行。

img

16.什么是Spring事务的隔离级别?

spring 有五大隔离级别,默认值为 ISOLATION_DEFAULT(使用数据库的设置),其他四个隔离级别和数据库的隔离级别一致:

  1. ISOLATION_DEFAULT:用底层数据库的设置隔离级别,MySQL默认的为ISOLATION_REPEATABLE_READ。
  2. ISOLATION_READ_UNCOMMITTED:读未提交,最低的隔离级别,一个事务可以读取另一个事务更新但未提交的数据。(会出现脏读、不可重复读、幻读);
  3. ISOLATION_READ_COMMITTED:读已提交,一个事务提交后才能被其他事务读取到(会出现不可重复读、幻读),Oracle、SQL server 的默认级别;
  4. ISOLATION_REPEATABLE_READ:可重复读,对同一字段的多次读取结果都是一致的,除非数据被本身事务所修改(会出现幻读),MySQL 的默认级别;
  5. ISOLATION_SERIALIZABLE:可串行化,最高的隔离级别,可以防止脏读、不可重复读、幻读。

img

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

gateway 过滤器执行顺序_spring boot gateway 过滤器的执行顺序

前言学习官方文档&#xff0c;发现对于过滤器有分为三类默认过滤器自定义过滤全局过滤器于是就有一个疑问&#xff0c;关于这些过滤器的访问顺序是怎样的&#xff0c;今天就以一个demo来进行测试准备阶段过滤器工厂类以此为模板&#xff0c;复制出几份就可以了&#xff0c;注意…

Java 线程状态流转

Java 线程一共有 6 种状态&#xff1a; NEW&#xff1a;新建状态&#xff0c;当一个线程被创建完成&#xff0c;还没有调用 start() 方法时&#xff0c;是这种状态。RUNNABLE&#xff1a;可运行状态&#xff0c;当一个线程正在正常地执行 run() 中的代码时&#xff0c;是这种状…

达梦数据库导入oracle数据_达梦数据库和oracle数据的一些区别

近期我在考达梦的dca发现有一些和oracle不同的地方&#xff0c;由于我是oracleDBA在维护达梦数据库的时候有需要注意的地方&#xff0c;现在分享一下2个数据库的一些区别。1、登陆的区别oracle:如果sys的密码忘记可以用操作系统验证方式登陆修改密码。dm:达梦数据库如果忘记了s…

Fail-fast 和 Fail-safe 机制

fail-fast 和 fail-safe 的区别 从字面意思来看 fail-fast 是快速失败&#xff0c;fail-safe 是安全失败&#xff0c;这都是集合类对于并发读写时的一种应对机制。 fail-fast&#xff0c;广泛应用于 java.util 下的集合类中&#xff0c;其机制为在使用迭代器遍历的过程中&…

【java8新特性】——lambda表达式与函数式接口详解(一)

一、简介 java8于2014年发布&#xff0c;相比于java7&#xff0c;java8新增了非常多的特性&#xff0c;如lambda表达式、函数式接口、方法引用、默认方法、新工具&#xff08;编译工具&#xff09;、Stream API、Date Time API、Optional等 。 当前很多公司的老产品依然使用的…

详解 ConcurrentHashMap

文章目录ConcurrentHashMap 的底层数据结构?ConcurrentHashMap 的带参构造方法的流程&#xff1f;ConcurrentHashMap 的 put 方法的流程?ConcurrentHashMap addCount 方法的流程是怎样的呢&#xff1f;ConcurrentHashMap transfer 方法的流程是怎样的呢&#xff1f;Concurren…

js 二叉树图形_js数据结构和算法(三)二叉树

二叉树的概念二叉树(Binary Tree)是n(n>0)个结点的有限集合&#xff0c;该集合或者为空集(空二叉树)&#xff0c;或者由一个根结点和两棵互不相交的、分别称为根结点的左子树和右子树的二叉树组成。二叉树的特点每个结点最多有两棵子树&#xff0c;所以二叉树中不存在度大于…

【java8新特性】——Stream API详解(二)

一、简介 java8新添加了一个特性&#xff1a;流Stream。Stream让开发者能够以一种声明的方式处理数据源&#xff08;集合、数组等&#xff09;&#xff0c;它专注于对数据源进行各种高效的聚合操作&#xff08;aggregate operation&#xff09;和大批量数据操作 (bulk data op…

Spring bean 不被 GC 的真正原因

概述 自从开始接触 Spring 之后&#xff0c;一直以来都在思考一个问题&#xff0c;在 Spring 应用的运行过程中&#xff0c;为什么这些 bean 不会被回收&#xff1f; 今天深入探究了这个问题之后&#xff0c;才有了答案。 思考点 大家都知道&#xff0c;一个 bean 会不会被回…

ad域时间源配置_域控制器server2012时间同步NTP配置

一、域控配置1.修改注册表&#xff0c;设置域控服务器名称2.设置组策略&#xff0c;启动NTP服务器3.域策略中设置windows time服务自动启动二、服务端配置(Ntp服务器&#xff0c;客户端将根据这台服务器的时间进行同步)1、微软键R键&#xff0c;进入“运行”&#xff0c;输入“…

【java8新特性】——Optional详解(三)

一、简介 Optional类是Java8为了解决null值判断问题&#xff0c;借鉴google guava类库的Optional类而引入的一个同名Optional类&#xff0c;使用Optional类可以避免显式的null值判断&#xff08;null的防御性检查&#xff09;&#xff0c;避免null导致的NPE&#xff08;NullPo…

不使用 + 和 - 运算符计算两整数之和

问题概述 不使用运算符 和 -&#xff0c;计算两整数之和 思考 不使用 和 - &#xff0c;那就只能想到用位运算来处理了。思路如下&#xff1a; 两数进行 ^&#xff08;异或运算&#xff09;&#xff0c;可以得到两个数在相同位上数值不同的相加结果两数进行 &&#x…

vts传感器采取船舶的_详解虎门大桥监测系统:传感器与物联网功不可没

来源&#xff1a;传感器专家网近日&#xff0c;虎门大桥“虎躯一震”给全国人民来了个“深呼吸”。虎门大桥是广东沿海地区重要的交通枢纽&#xff0c;始建于1992年&#xff0c;1997年通车至今&#xff0c;大桥一直都十分平稳。但在5月5日下午&#xff0c;虎门大桥发生异常抖动…

宝塔安装sqlserver_linux宝塔面板安装安装 pdo_sqlsrv扩展

第一步安装源curl https://packages.microsoft.com/config/rhel/7/prod.repo > /etc/yum.repos.d/mssqlrelease.repo第二步安装驱动yum install msodbcsql mssql-tools unixODBC-devel第三步下载pdo-sqlsrv源码wget http://pecl.php.net/get/pdo_sqlsrv-5.6.1.tgztar -zxvf …

【java8新特性】——方法引用(四)

一、简介 方法引用是java8的新特性之一&#xff0c; 可以直接引用已有Java类或对象的方法或构造器。方法引用与lambda表达式结合使用&#xff0c;可以进一步简化代码。 来看一段简单代码&#xff1a; public static void main(String[] args) {List<String> strList Ar…

MySQL 排名函数.md

概述 MySQL 自带的排名的函数&#xff0c;主要有&#xff1a; row_number()rank()dense_rank()ntile() 测试数据 测试数据如下所示&#xff1a; row_number() 函数 用法如下&#xff1a; SELECT row_number() OVER (ORDER BY Salary DESC) row_num,Salary FROMEmployee查…

【java8新特性】——默认方法(五)

一、简介 默认方法是指接口的默认方法&#xff0c;它是java8的新特性之一。顾名思义&#xff0c;默认方法就是接口提供一个默认实现&#xff0c;且不强制实现类去覆写的方法。默认方法用default关键字来修饰。 默认方法可以解决的痛点&#xff1a; 在java8之前&#xff0c;修…

Java 序列化总结.md

概述 序列化&#xff1a;将对象写入到 IO 流中反序列化&#xff1a;从 IO 流中恢复对象 实现方法 实现 Serializable 或者 Externalizable Serializable&#xff1a;标记接口&#xff0c;不用实现任何方法&#xff0c;可以指定序列化 IDExternalizable&#xff1a;增强的序…

多线程买票案例

测试类 package thead;public class testThread {public static void main(String [] arg){Tickets ticket new Tickets();Thread t1 new Thread(ticket,"窗口一&#xff1a;");Thread t2 new Thread(ticket,"窗口二&#xff1a;");Thread t3 new Thr…

深度学习auc_机器学习集成学习与模型融合!

↑↑↑关注后"星标"Datawhale每日干货 & 每月组队学习&#xff0c;不错过Datawhale干货 作者&#xff1a;李祖贤&#xff0c;深圳大学&#xff0c;Datawhale高校群成员对比过kaggle比赛上面的top10的模型&#xff0c;除了深度学习以外的模型基本上都是集成学习的…