Java 如何在spring中仅使用@scope(“prototype”)注释创建bean原型?

Java 如何在spring中仅使用@scope(“prototype”)注释创建bean原型?,java,spring,Java,Spring,我有这堂课 public class Draw { public static void main(String[] args) { ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml"); Triangle t = (Triangle) context.getBean("triangle"); Triangle t1 = (Triang

我有这堂课

public class Draw {
    public static void main(String[] args) {
        ApplicationContext  context = new ClassPathXmlApplicationContext("spring.xml");

        Triangle t = (Triangle) context.getBean("triangle");
        Triangle t1 = (Triangle) context.getBean("triangle");

        t.show();

        System.out.println(t == t1);

    }
}
三角形类

@Service
@Scope("prototype")
public class Triangle {
    private Point pointa;

    public Point getPointa() {
        return pointa;
    }

    public Triangle(Point pointa) {
        this.pointa = pointa;
    }

    public void show() {
        System.out.println("POINT A (" + pointa.getX() + "," + pointa.getY() + ")");

    }

    @Override
    public String toString() {
        return "Triangle [pointa=" + pointa + "]";
    }
}
和SPRING.XML

<context:component-scan base-package="com.spring.demo" />
<mvc:annotation-driven />
<context:component-scan base-package="com.spring.demo" />
<bean id="triangle" class="com.spring.demo.Triangle" autowire="constructor">
</bean>

<bean id="pointabc" class="com.spring.demo.Point">
    <property name="x" value="0" />
    <property name="y" value="0" />
</bean>

<context:annotation-config />

由于ApplicationContext有几个实现,ClassPathXmlApplicationContext一个用于XMLBean配置

在XML方式中,您只需在bean元素中设置scope属性

AnnotationConfigApplicationContext是ApplicationContext的实现,用于基于Java的配置,用于基于注释的配置,如@Bean等

如果要使用注释方式,则需要定义基于Java的配置,并需要使用注释ConfigApplicationContext对象

@Configuration
public class AppConfiguration{
   @Bean 
   @Scope("prototype")
   public Triangle triangle(){
      return new Triangle();
   }
}
然后获得如下所示的bean

  ApplicationContext ctx = 
         new AnnotationConfigApplicationContext(AppConfiguration.class);

      Triangle triangle= ctx.getBean(Triangle.class);

Triangle
声明为
prototype
无效,因为它在
spring.xml
中被实例化为singleton

关键是每次需要一个新的原型bean时,都要请求一个新的原型bean


这可以通过使用配置类(并删除注释配置的
来实现,我们使用注释配置应用程序上下文一个抽象应用程序的实现上下文

public class Scope{

    public static void main(String[] args) {
    AbstractApplicationContext context = new AnnotationConfigApplicationContext(TeacherConfig.class);
    Teacher tea=(Teacher) context.getBean("teacher");
    Teacher tea1=(Teacher) context.getBean("teacher");
    System.out.println(tea==tea1);
        }

}
教师班

public class Teacher {
public void print(String msg){
    System.out.println("TEACHER -->"+msg);
}
教师配置

@Configuration
public class TeacherConfig {

    @Bean(name = "teacher")
    @Scope(value=ConfigurableBeanFactory.SCOPE_SINGLETON)
    public Teacher Teacher() {
        return new Teacher();
    }
}
@Configuration告诉Spring这是相当于Spring.xml的核心Spring配置文件,并通过@bean定义bean。


System.out.println(tea==tea1);
的输出是TRUE

通过扩展@AshishUpadhyay给出的答案,我在代码中做了几处更改。上面的答案是针对单例范围的。对于原型,需要做一些更改

import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.AbstractApplicationContext;


public class Scope{

    public static void main(String[] args) {
    AbstractApplicationContext context = new AnnotationConfigApplicationContext(TeacherConfig.class);
    Teacher tea=(Teacher) context.getBean(Teacher.class);
    Teacher tea1=(Teacher) context.getBean(Teacher.class);
    System.out.println(tea);
    System.out.println(tea1);
    System.out.println(tea==tea1);
        }

}
教师班:

public class Teacher {
    public void print(String msg) {
        System.out.println("TEACHER -->" + msg);
    }
}
教师配置类:

import org.springframework.beans.factory.config.ConfigurableBeanFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;

@Configuration
public class TeacherConfig {

    @Bean()
    @Scope(value=ConfigurableBeanFactory.SCOPE_PROTOTYPE)
    public Teacher Teacher() {
        return new Teacher();
    }
}
运行Scope类后,输出为false,这是原型的预期结果


希望这能对其他人有所帮助。

现在spring说默认构造函数必须是presenty,因为您已经定义了参数化构造函数,这就是为什么
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.AbstractApplicationContext;


public class Scope{

    public static void main(String[] args) {
    AbstractApplicationContext context = new AnnotationConfigApplicationContext(TeacherConfig.class);
    Teacher tea=(Teacher) context.getBean(Teacher.class);
    Teacher tea1=(Teacher) context.getBean(Teacher.class);
    System.out.println(tea);
    System.out.println(tea1);
    System.out.println(tea==tea1);
        }

}
public class Teacher {
    public void print(String msg) {
        System.out.println("TEACHER -->" + msg);
    }
}
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;

@Configuration
public class TeacherConfig {

    @Bean()
    @Scope(value=ConfigurableBeanFactory.SCOPE_PROTOTYPE)
    public Teacher Teacher() {
        return new Teacher();
    }
}