新手求教,获取 bean 可以 return this 么

2022-09-30 09:47:06 +08:00
 NoKey

有一个 bean

@Component
public class DemoParam {
}

然后,我有个类,不能通过注入的方式拿到这个 bean 的对象

常规的方式是通过 context 去获取

但是我觉得这样写出来不好看,还无法复用

于是我在DemoParam中写了几个方法

 private static DemoParam demoParam;
 @PostConstruct
 public void init(){
 	demoParam = this;
 }
 public static DemoParam instance(){
 	return demoParam;
 }

这样,我只需要调用instance()方法,就可以拿到 spring 创建的这个 bean 对象

请教一下大家,这样有没啥弊端呢,谢谢

2939 次点击
所在节点    程序员
31 条回复
NoKey
2022-09-30 11:21:01 +08:00
@facelezz 单就这个问题进行讨论,我的想法是,把赋值放在 @PostConstruct 中,这个是 servlet 执行时必然调用一次,那么只要是服务可用状态,赋值肯定被执行了,然后,在单例模式下,这个就是对一个对象变量,应该没有线程安全问题
NoKey
2022-09-30 11:21:16 +08:00
@zmal 感谢,明白这个问题了
zmal
2022-09-30 11:22:20 +08:00
@facelezz 这里没有 happen-before 问题,@PostConstruct 注解在 springboot 启动该对象初始化后已经执行了。
happen-before 也不是这么用的。
facelezz
2022-09-30 11:29:28 +08:00
@zmal 你说的应该是 实例方法下 获取没这个问题 因为注入时的获取 是 spring 在 map 上加锁才有先后顺序(lock-unlock) 楼主直接请求的静态方法静态变量 正常来讲是没有这个保证的
facelezz
2022-09-30 11:33:21 +08:00
@zmal
@NoKey
对这个问题有疑惑的话 可以参考 https://stackoverflow.com/questions/23906808/should-i-mark-object-attributes-as-volatile-if-i-init-them-in-postconstruct-in
里面讲了一般情况下 为什么没有可见性( happen-before )问题
Bronya
2022-09-30 13:30:27 +08:00
所以结论是啥呀,楼主这么写到底有没有问题,是不是在没有增强时(@Transactional 或者其他 aop )楼主这么写也可以的?
NoKey
2022-09-30 15:42:07 +08:00
@Bronya 我理解的是,保险起见,还是用 context
siweipancc
2022-09-30 17:24:22 +08:00
会寄,但是可以多测试一下,生命周期暂时稳定(服务器顺序不定)就行,爆了再说。
siweipancc
2022-09-30 17:37:23 +08:00
上边的提到非唯一问题,只要保证单栗模式+不允许覆盖定义就行。你这样写完全没有问题。

甚至可以定义成内部静态字段=context.get(),只要第一次方法引用时 app ready 就行
duteliang
2022-09-30 18:43:10 +08:00
不会有问题的,但是要保证这个静态方法不要在项目启动,初始化的时候调用。不然因为 bean 的加载顺序问题有概率空指针。
liuzhaowei55
2022-09-30 18:56:44 +08:00
直接写个单例,然后自己 new 这个类?现在这样怪怪的,或者参考下许多 BeanUtils 的写法,都可以不用注入 context 静态获取实例,关键字如 cola- domains

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/883960

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX