简体   繁体   English

如何在Spring中保留静态类变量的值?

[英]How do I keep the value of a static class variable in Spring?

so I have this class example: 所以我有这个类的例子:

public class Test {

    private static int idCounter;
    private int id;

    Test() {
        id=++idCounter;
    }

    public void getId() {
        System.out.printf("This id is %s",this.id);
    }
}

And the beans.xml config: 而且beans.xml配置:

<beans>
    <bean id="test" class="com.Test"/>
</beans>

Now when I try to make an ArrayList, the static variable resets every time. 现在,当我尝试创建一个ArrayList时,静态变量每次都会重置。

for (int i=0;i<9;i++) {
    arrayList.add(context.getBean("test");
    arrayList.get(i).getId();
}

It will print that "This is is 1" for every object in the arrayList. 它将为arrayList中的每个对象打印“This is is 1”。 How can I make it so that the static variable will keep it's global value? 我怎样才能使静态变量保持全局值?

What is happening here is not what you think is happening. 这里发生的事情不是你认为发生的事情。 The static member variable is not resetting; 静态成员变量没有重置; there is only one instance of your Test bean, and in the loop you are looking up the same Test bean ten times. 你的Test bean只有一个实例,在循环中你会查找相同的Test bean十次。

Spring beans by default have singleton scope, which means Spring will create only one instance of the bean, which is used every time it is injected or looked up. Spring bean默认具有singleton范围,这意味着Spring只会创建一个bean实例,每次注入或查找时都会使用它。 If you want a new instance created every time, give the bean prototype scope instead of the default singleton scope: 如果您希望每次都创建一个新实例,请给出bean原型范围而不是默认的单例范围:

@Scope("prototype")
public class Test {
    // ...
}

If you configure your Spring beans using XML, then do it as Andrew Logvinov shows in his answer; 如果您使用XML配置Spring bean,那么就像Andrew Logvinov在他的回答中所显示的那样; add a scope attribute: 添加scope属性:

<bean id="test" class="com.Test" scope="prototype"/>

To learn more, see Bean scopes in the Spring Framework reference documentation. 要了解更多信息,请参阅Spring Framework参考文档中的Bean作用域

By default, Spring beans have singleton scope, meaning each request returns same instance of bean. 默认情况下,Spring bean具有单例范围,这意味着每个请求都返回相同的bean实例。 What you need is a prototype scope: 你需要的是一个原型范围:

<bean id="myBean" class="com.test.MyClass" scope="prototype"/>

You have declared you bean with test id: 您已使用test ID声明了bean:

<beans>
    <bean id="test" class="com.Test"/>
</beans>

But after that you get instance of some another bean using id triangle : 但之后你会使用id triangle获得另一个bean的实例:

context.getBean("triangle")

So, I suppose, this is just typo-error: you obtain instance of some another bean, where you don't have static id counter. 所以,我想,这只是错字错误:你获得了另一个bean的实例,你没有静态id计数器。 Check you code and update question if I'm not right. 如果我不对,请检查您的代码并更新问题。

Jesper's answer is right; Jesper的回答是正确的; since you configured this as as singleton there is only one instance of the class, the constructor gets called once. 因为你将它配置为单例,只有一个类的实例,构造函数被调用一次。

However, even once you fix that this to use prototype scope it may not work as you expect, for two reasons: 但是,即使你修复了这个以使用原型范围,它也可能无法按预期工作,原因有两个:

You should use something like AtomicInteger for this, it will allow threadsafe incrementing and provide visibility guarantees. 你应该使用像AtomicInteger这样的东西,它将允许线程安全递增并提供可见性保证。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM