当前位置: 首页 > news >正文

商城网站建设 上海seo发帖软件

商城网站建设 上海,seo发帖软件,郑州网站建设哪家公司好,crm登录系统目录 一、spring当中有哪些scope 二、scope初始化与销毁演示 2.1 scope的初始化 2.2 scope的销毁 三、scope失效及其解决方案 3.1 scope失效演示 3.2 scope失效解决方案一:Lazy 3.3 scope失效解决方案二:设置proxyMode属性 3.4 scope失效解决…

目录

一、spring当中有哪些scope

二、scope初始化与销毁演示

2.1 scope的初始化 

2.2 scope的销毁

三、scope失效及其解决方案 

3.1 scope失效演示

3.2 scope失效解决方案一:@Lazy 

3.3 scope失效解决方案二:设置proxyMode属性

3.4 scope失效解决方案三:ObjectFactory

3.5  scope失效解决方案四:ApplicationContext容器

3.6 总结


 

一、spring当中有哪些scope

        我使用的spring版本是5.3.10,其中scope有五种:

  • singleton:从spring中获取bean时,每次获取的是同一个bean

  • prototype:从spring中获取bean时,每次获取的是新的bean

  • request:生成的bean存活于request域中,生命周期也与request相同

  • session:生成的bean存活于session域中,生命周期也与session相同

  • application:生成的bean存活于application域中,生命周期也与application相同(spring中的application指的是servletContext)

二、scope初始化与销毁演示

2.1 scope的初始化 

        主启动类:

@SpringBootApplication
public class A08 {public static void main(String[] args) {SpringApplication.run(A08.class, args);}
}

        主启动类启动后,就会扫描到下面的三个bean:

@Scope("request")
@Component
public class BeanForRequest {private static final Logger log = LoggerFactory.getLogger(BeanForRequest.class);@PreDestroypublic void destroy() {log.debug("destroy");}
}
@Scope("session")
@Component
public class BeanForSession {private static final Logger log = LoggerFactory.getLogger(BeanForSession.class);@PreDestroypublic void destroy() {log.debug("destroy");}
}
@Scope("application")
@Component
public class BeanForApplication {private static final Logger log = LoggerFactory.getLogger(BeanForApplication.class);@PreDestroypublic void destroy() {log.debug("destroy");}
}

        这三个bean在controller中被用到:

@RestController
public class MyController {//MyController是单例,单例去使用其他的域,都要加@Lazy,否则会失效@Lazy@Autowiredprivate BeanForRequest beanForRequest;@Lazy@Autowiredprivate BeanForSession beanForSession;@Lazy@Autowiredprivate BeanForApplication beanForApplication;@GetMapping(value = "/test", produces = "text/html")public String test(HttpServletRequest request, HttpSession session) {ServletContext sc = request.getServletContext();String sb = "<ul>" +"<li>" + "request scope:" + beanForRequest + "</li>" +"<li>" + "session scope:" + beanForSession + "</li>" +"<li>" + "application scope:" + beanForApplication + "</li>" +"</ul>";return sb;}
}

        打开不同的浏览器, 刷新 http://localhost:8080/test 即可查看效果。如果 jdk > 8, 运行时请添加 --add-opens java.base/java.lang=ALL-UNNAMED

        打开一个浏览器(例如:Chrome)可以发现,每次刷新都可以看到request域的bean不一样,说明每次创建的是新的bean,request的bean会在请求结束后销毁。

        再打开一个浏览器(例如:edge)可以发现,会话域的bean也不同,是因为每个浏览器都会创建自己的会话。

         打开不同的浏览器也能看到,request和session的bean不相同,是因为每个浏览器都有自己的请求和会话域;而application的bean时相同的,因为他们对应的是同一个web应用程序

2.2 scope的销毁

  • singleton,容器启动时创建(未设置延迟),容器关闭时销毁

  • prototype,每次使用时创建,不会自动销毁,需要调用DefaultListableBeanFactory.destroyBean(bean) 销毁

  • request,每次请求用到此 bean 时创建,请求结束时销毁

  • session,每个会话用到此 bean 时创建,会话结束时销毁

  • application,web 容器用到此 bean 时创建,容器停止时销毁

        在浏览器中每次刷新我们都可以看到控制台打印出了beanForRequest的销毁方法,这是因为每次刷新都代表着一个请求结束了;session销毁时间默认为30min,为了方便演示,我们在application.properties文件中设置

server.servlet.session.timeout=10s

         这样session就可以在1min后自动销毁了(spring内部设置session销毁时间低于1min就视为1min,这篇文章剖析了这部分源码:SpringBoot设置Session失效时间 - 简书),我们可以在控制台上看到session销毁的日志

image-20220402144856449 

三、scope失效及其解决方案 

3.1 scope失效演示

        以单例注入多例为例(单例注入其他类型的scope也是同理),先看看主启动类:

@ComponentScan("com.itheima.a08.sub")
public class A08_1 {private static final Logger log = LoggerFactory.getLogger(A08_1.class);public static void main(String[] args) {AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(A08_1.class);E e = context.getBean(E.class);log.debug("{}", e.getF1().getClass());log.debug("{}", e.getF1());log.debug("{}", e.getF1());log.debug("{}", e.getF1());context.close();}
}

        在主启动类中,我们先通过getBean方法拿到E的对象,再通过get方法拿到e中注入的f1对象。E并没有加@prototype注解,所以默认是个单例,而f1是个多例。

@Component
public class E {@Autowiredprivate F1 f1;public F1 getF1() {return f1;}
}
@Scope("prototype")
@Component
public class F1 {
}

        那么问题来了,我们在主启动类中多调用几次,每次返回的f1对象是同一个对象还是不同对象?我们既然将F1标注为多例,自然是期望返回不同对象的。

        然而运行可得,每次返回的都是同一对象 :

         原因是:对于单例对象来讲,依赖注入仅发生一次,后续再没有发生依赖注入,E再没有用到多例的F1,因此E用的始终是第一次依赖注入的F1。

3.2 scope失效解决方案一:@Lazy 

        我们在成员变量或者使用的方法上加上@Lazy注解,@Lazy能够帮助我们生成代理对象,这样,代理对象虽然还是同一个,但当每次使用代理对象的任意方法时,由代理创建新的f1对象。 

@Component
public class E {@Lazy@Autowiredprivate F1 f1;public F1 getF1() {return f1;}
}

        运行发现每次生成的bean已经不一样了。我们也打印一下e.getF1().getClass,看看生成的F1的真实类型,可以看到并不是F1,而是代理增强的类。

3.3 scope失效解决方案二:设置proxyMode属性

        我们还可以在被调用的多例类上设置 proxyMode 属性,我们用F2来演示这个解决办法:

@Scope(value = "prototype", proxyMode = ScopedProxyMode.TARGET_CLASS)
@Component
public class F2 {
}

        这个方法的本质也是生成代理。运行后可以看到,生成的bean也不一样了,获取到的F2的真实类型也是代理增强的类。 

3.4 scope失效解决方案三:ObjectFactory

        我们可以在E中注入的时候将F声明为 ObjectFactory 类型,这样每次获取的时候都由工厂生成不同的F。我们用F3来演示这个解决办法:

@Component
public class E {@Autowiredprivate ObjectFactory<F3> f3;public F3 getF3() {return f3.getObject();}
}
@Scope("prototype")
@Component
public class F3 {
}

3.5  scope失效解决方案四:ApplicationContext容器

        直接实现容器,利用容器的getBean方法来获取F多例bean。我们用F4来演示:

@Component
public class E {@Autowiredprivate ApplicationContext context;public F4 getF4() {return context.getBean(F4.class);}
}
@Scope("prototype")
@Component
public class F4 {
}

3.6 总结

        虽然上述四种方法各不相同,但理念基本相同,都是延迟其他scope bean的获取。他们都是不直接获取多例,而是在中间加一个对象,通过这个对象等到运行时再去获取多例bean 

        更推荐使用BeanFactory 或 ApplicationContext,因为更加简洁,且不像代理一样会造成一定的性能损耗。

http://www.hkea.cn/news/616791/

相关文章:

  • 网站建设课程简介图片百度官网认证免费
  • 月夜影视在线观看免费完整版韩剧关键词排名优化报价
  • 做网站的工作时间兰州seo公司
  • css怎么嵌入到html直通车关键词优化口诀
  • 虚拟网站php专业型seo网站关键词排名提升
  • 找人合伙做网站平台b2b电商平台
  • 手机网站建设技术方案找网站设计公司
  • 杭州如何设计公司网站惠州seo网站推广
  • 成都网站建设门户大连企业网站建站模板
  • 游戏卡充值可以做网站吗百度竞价关键词出价技巧
  • 建设企业网站就等于开展网络营销网店推广实训报告
  • dede无法更新网站主页到百度联盟注册
  • wordpress支持爱奇艺企业网站seo托管怎么做
  • 永川做网站的武汉百度快速排名提升
  • 做网站的故意给中病毒网络营销广告
  • 关于阅读类网站的建设规划书友情链接系统
  • 专业做幼儿园设计的网站百度小程序关键词优化
  • 腾龙时时彩做号网站整站优化关键词排名
  • 正规的网站制作与推广百度广告运营
  • 网站建设估价引擎搜索有哪些
  • 东莞网站建设选菲凡网络如何制作网站
  • 网站收录系统备案查询官网
  • 临朐县网站建设利用搜索引擎营销成功的案例
  • 利用网盘做视频网站镇江优化推广
  • 视频微网站开发哪个公司网站设计好
  • 品网站建设智能搜索引擎
  • 怎样在百度建网站seo建设者
  • 四海网络网站建设咨询什么叫做网络营销
  • 安徽建设网官方网站优化分析
  • 网站根目录文件名游戏推广员是做什么的