zoukankan      html  css  js  c++  java
  • annotation之@Autowired、@Inject、@Resource三者区别和示例

    @Autowired注解

    1、@Autowired是spring自带的注解,通过‘AutowiredAnnotationBeanPostProcessor’ 类实现的依赖注入;

    2、@Autowired是根据类型进行自动装配的,如果需要按名称进行装配,则需要配合@Qualifier;

    3、@Autowired有个属性为required,可以配置为false,如果配置为false之后,当没有找到相应bean的时候,系统不会抛错;

    4、@Autowired可以作用在变量、setter方法、构造函数上。

    @Autowired配合@Qualifier使用

    @Qualifier:限定描述符,用于细粒度选择候选者
    在这里插入图片描述
    @Autowired默认是根据类型进行注入的,因此如果有多个类型一样的Bean候选者,则需要限定其中一个候选者,否则将抛出异常。

    @Qualifier限定描述符除了能根据名字进行注入,更能进行更细粒度的控制如何选择候选者

    根据基于XML配置中的<qualifier>标签指定的名字进行注入,使用如下方式指定名称:
    其中type属性可选,指定类型,默认就是Qualifier注解类name就是给Bean候选者指定限定标识符

    <bean id="springQualifierTestService1" class="xx.SpringQualifierTestServiceImpl1">
       <qualifier type="org.springframework.beans.factory.annotation.Qualifier" value="springQualifierTestService1"/>
    </bean>
    

    一个Bean定义中只允许指定类型不同的<qualifier>,如果有多个相同type后面指定的将覆盖前面的

    • 缺省的根据Bean名字注入:

      是在Bean上没有指定<qualifier>标签时一种容错机制,即缺省情况下使用Bean标识符注入
      (下文的使用举例即是在Bean缺少@qualifier标签,通过容错机制使用Bean标识)
      但如果你指定了标签将不会发生容错。

    使用举例一(缺少容错根据Bean名字注入):
    SpringQualifierTestService.java

    public interface SpringQualifierTestService {
    
    	public String getId();
    
    }
    

    SpringQualifierTestServiceImpl1.java

    import java.util.UUID;
    
    import org.springframework.stereotype.Service;
    
    @Service("springQualifierTestService1")
    public class SpringQualifierTestServiceImpl1 implements SpringQualifierTestService {
    
    	private String uuid;
    	
    	public SpringQualifierTestServiceImpl1() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("SpringQualifierTestServiceImpl1实例化"+uuid);
    	}
    	
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    

    SpringQualifierTestServiceImpl2.java

    import java.util.UUID;
    
    import org.springframework.stereotype.Service;
    
    @Service("springQualifierTestService2")
    public class SpringQualifierTestServiceImpl2 implements SpringQualifierTestService {
    
    	private String uuid;
    
    	public SpringQualifierTestServiceImpl2() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("SpringQualifierTestServiceImpl2实例化" + uuid);
    	}
    
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    

    SpringQualifierTestController.java

    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.beans.factory.annotation.Qualifier;
    import org.springframework.stereotype.Controller;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    
    @Controller
    public class SpringQualifierTestController {
    	
    	@Autowired
    	@Qualifier("springQualifierTestService1")
    	SpringQualifierTestService springQualifierTestService;
    	
    	@RequestMapping(value = "spring/qualifier/test", method = RequestMethod.GET)
    	public void testScopeSession() {
    		
    		System.out.println(springQualifierTestService.getId());
    	}
    }
    

    使用举例二(扩展@Qualifier限定描述符注解):

    QualifierService1.java

    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    import javax.inject.Qualifier;
    
    @Documented
    @Retention(RetentionPolicy.RUNTIME)
    @Qualifier
    @Target(value = { ElementType.FIELD, ElementType.PARAMETER, ElementType.TYPE })
    public @interface QualifierService1 {
    	
    }
    

    QualifierService2.java

    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    import javax.inject.Qualifier;
    
    @Documented
    @Retention(RetentionPolicy.RUNTIME)
    @Qualifier
    @Target(value = { ElementType.FIELD, ElementType.PARAMETER, ElementType.TYPE })
    public @interface QualifierService2 {
    	
    }
    

    SpringQualifierTestServiceImpl1.java

    import java.util.UUID;
    
    import org.springframework.stereotype.Service;
    
    @Service
    @QualifierService1
    public class SpringQualifierTestServiceImpl1 implements SpringQualifierTestService {
    
    	private String uuid;
    	
    	public SpringQualifierTestServiceImpl1() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("SpringQualifierTestServiceImpl1实例化"+uuid);
    	}
    	
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    

    SpringQualifierTestServiceImpl2.java

    import java.util.UUID;
    
    import org.springframework.stereotype.Service;
    
    @Service
    @QualifierService2
    public class SpringQualifierTestServiceImpl2 implements SpringQualifierTestService {
    
    	private String uuid;
    
    	public SpringQualifierTestServiceImpl2() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("SpringQualifierTestServiceImpl2实例化" + uuid);
    	}
    
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    

    SpringQualifierTestController.java

    
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Controller;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    
    @Controller
    public class SpringQualifierTestController {
    	
    	                   
    	@Autowired
    	@QualifierService2
    	SpringQualifierTestService springQualifierTestService;
    	
    	@RequestMapping(value = "spring/qualifier/test", method = RequestMethod.GET)
    	public void testScopeSession() {
    		
    		System.out.println(springQualifierTestService.getId());
    	}
    }
    

    @Inject注解

    1、@Injec
    t是JSR330 (Dependency Injection for Java)中的规范,需要导入javax.inject.Inject;实现注入。

    2、@Inject是根据类型进行自动装配的,如果需要按名称进行装配,则需要配合@Named

    3、@Inject可以作用在变量、setter方法、构造函数上

    @Named

    @Named和Spring的@Component功能相同。@Named可以有值,如果没有值生成的Bean名称默认和类名相同。
    例如:

    1. @Named public class Person
      该bean的名称就是person。
    2. @Named(“p”) public class Person
      该bean的名称就是p。

    @Inject配合@Qualifier使用

    任何人都可以定义一个新的修饰语,一个qualifier注解应该满足如下条件:
    ● 定义的注解类有@Qualifier,@Retention(RUNTIME)和@Documented。
    ● 可以有属性
    ● 可以是公共API的一部分
    ● 可以用@Target注解限定使用范围

    下面是Qualifier的例子:

    pom.xml

    <dependency>
    	<groupId>javax.inject</groupId>
    	<artifactId>javax.inject</artifactId>
    	<version>1</version>
    </dependency>
    

    Genre.java

    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    import javax.inject.Qualifier;
    
    @Documented
    @Retention(RetentionPolicy.RUNTIME)
    @Qualifier
    @Target(value = { ElementType.FIELD, ElementType.PARAMETER, ElementType.TYPE })
    public @interface Genre {
    	QualifierService qualifierService() default QualifierService.QUALIFIERSERVICE1;
    
    	public enum QualifierService {
    		QUALIFIERSERVICE1, QUALIFIERSERVICE2
    	}
    }
    

    QualifierTestService.java

    public interface QualifierTestService {
    
    	public String getId();
    
    }
    

    QualifierTestServiceImpl1.java

    import java.util.UUID;
    import javax.inject.Named;
    
    @Named
    @Genre(qualifierService = QualifierService.QUALIFIERSERVICE1)
    public class QualifierTestServiceImpl1 implements QualifierTestService {
    
    	private String uuid;
    
    	public QualifierTestServiceImpl1() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("QualifierTestServiceImpl1实例化" + uuid);
    	}
    
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    

    QualifierTestServiceImpl2.java

    import java.util.UUID;
    import javax.inject.Named;
    
    @Named
    @Genre(qualifierService = QualifierService.QUALIFIERSERVICE2)
    public class QualifierTestServiceImpl2 implements QualifierTestService {
    
    	private String uuid;
    
    	public QualifierTestServiceImpl2() {
    		uuid = UUID.randomUUID().toString();
    		System.out.println("QualifierTestServiceImpl2实例化" + uuid);
    	}
    
    	@Override
    	public String getId() {
    		// TODO Auto-generated method stub
    		return uuid;
    	}
    
    }
    
    

    QualifierTestController.java

    import javax.inject.Inject;
    
    import org.springframework.stereotype.Controller;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    
    import com.gm.test16.Genre.QualifierService;
    
    @Controller
    public class QualifierTestController {
    
    	/*对QualifierTestService类的注入,如果对QualifierTestService类注入应该是:@Genre(qualifierService = QualifierService.QUALIFIERSERVICE1)或@Genre,因为@Genre默认的是QUALIFIERSERVICE1*/  
    	@Inject
    	@Genre(qualifierService = QualifierService.QUALIFIERSERVICE2)
    	QualifierTestService qualifierTestService;
    
    	@RequestMapping(value = "qualifier/test", method = RequestMethod.GET)
    	public void testScopeSession() {
    
    		System.out.println(qualifierTestService.getId());
    	}
    }
    

    可参照上文的《使用举例二(扩展@Qualifier限定描述符注解)》进行扩展测试。

    @Resource

    1、@Resource是JSR250规范的实现,需要导入javax.annotation实现注入。

    2、@Resource是根据名称进行自动装配的,一般会指定一个name属性

    3、@Resource可以作用在变量、setter方法上

    总结:

    1、@Autowired是spring自带的,@Inject是JSR330规范实现的,@Resource是JSR250规范实现的,需要导入不同的包

    2、@Autowired、@Inject用法基本一样,不同的是@Autowired有一个request属性

    3、@Autowired、@Inject是默认按照类型匹配的,@Resource是按照名称匹配的

    4、@Autowired如果需要按照名称匹配需要和@Qualifier一起使用,@Inject和@Named一起使用

  • 相关阅读:
    IOS开发 网络发展史(NSURLProtocol)
    IOS开发 网络发展史(NSURLCach)
    IOS 开发 网络发展史(URLConnection)
    ios 网络开发(CFNetwork)
    MAC安装mysql
    conda 安装常用包
    从必应上拉取图片
    旋转数组中的二分查找
    东北大学 python模拟登录校园网(2019年6月启用新登录模式后)
    Ubuntu 安装Codeblocks
  • 原文地址:https://www.cnblogs.com/gmhappy/p/13457042.html
Copyright © 2011-2022 走看看