Spring注解(八) @Autowired

770 阅读1分钟

@Autowired

用途

通常是一个类中, 需要用到另一个类. @Autowired根据类型找到容器中对应的组件然后注入.

测试

配置包扫描, 扫描BookDao, BookService

@ComponentScan("com.alex.autowired")
@Configuration
public class BookConfig {
    @Bean("bookdao2")
    public BookDao bookDao2() {
        BookDao bookDao = new BookDao();
        bookDao.setId(1);
        bookDao.setName("alex");
        return bookDao;
    }
}

BookDao

@Repository
public class BookDao {
    private int id;
    private String name;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

}

BookService

@Service
public class BookService {

    @Autowired
    private BookDao bookDao1;

    public void getBookById() {
        bookDao.getId();
    }

    @Override
    public String toString() {
        return "BookService{" +
                "bookDao=" + bookDao +
                '}';
    }
}

测试代码

@Test
public void test3() {
    AnnotationConfigApplicationContext ioc = getIoc(BookConfig.class);
    printBeans(ioc);
    BookService bookService = ioc.getBean(BookService.class);
    System.out.println(bookService);
    BookDao bookDao = ioc.getBean(BookDao.class);
    System.out.println(bookDao);
}
// 结果
bookConfig
bookDao
bookService
BookService{bookDao=com.alex.autowired.BookDao@67d18ed7}
com.alex.autowired.BookDao@67d18ed7

结论:从BookService中拿到的的BookDao对象和从容器中直接拿到的BookDao对象是同一个, @Autowired相当于到容器中把对象BookDao传递给BookService中的BookDao

多个同类型bookDao注入

报错, 按照类型查找bean, 如果有多个相同类型的bean直接报错

 No qualifying bean of type 'com.alex.autowired.BookDao' available: expected single matching bean but found 2: bookDao,bookDao2

bookDao,bookDao2 两个相同类型的bean如何解决呢?

  • 首先错误是因为, 当容器有两个相同类型的BookDao对象时, 不能再同过getBean(xxx.class)获取, 显然是冲突了
BookDao bookDao = ioc.getBean(BookDao.class);
System.out.println(bookDao);
  • 其次@Autowired注入的时候, 对象名要和容器中的bean名字对应上, 这样才不会出错.
@Autowired
private BookDao bookDao;
  • 解决方法2
@Qulifier("bookDao") // 明确指定要装配的组件
@Autowired
private BookDao bookDao;

不装配 required=false

  • 如果容器中没有这个对象, 可以不装配
@Autowired(required=false) //不是必须的
private BookDao bookDao;

@primary

@primary // 指定这个bean首选装配
@Bean("bookdao2")
public BookDao bookDao2() {
    BookDao bookDao = new BookDao();
    bookDao.setId(1);
    bookDao.setName("alex");
    return bookDao;
}

@Resource

  • 属于java规范
  • 和Autowired作用一致都是装配, 但是是按照名称 不支持required不支持primary, 注意是按照名字装配
  • 推荐用Autowired