我们知道SpringIOC容器通过xml配置bean标签来创建对象,如果有多个类,我们需要在xml配置文件中写大量的bean标签,那有没有其他方式创建对象呢。当然有了那就是SpringIOC的注解开发,我们只需要在需要的类上添加注解就可以了。先来说一下常用注解,再实例。
1,@Component注解
1,@Component注解:
作用:修饰一个类,将这个类交给Spring容器管理,相当于在xml文件中添加了一个bean标签。
属性:value:用于指定bean的id。当我们不写时,它的默认值是当前类名,且首字母改小写
此注解有三个衍生注解(功能相同),也是修饰类:
@Controller:一般用于表现层注解。
@Service:一般用于服务层注解。
@Repository:一般用于数据访问层。
实例:创建一个maven工程,如下图:
UserService接口和接口实现类:
/*
* 保存用户接口
* */
public interface UserService {
/*
* 保存用户
* */
void saveUser();
}
/*
*@Component注解
* 作用:把资源让spring来管理。相当于在xml中配置一个 bean。<bean id="" class="" scope=""></bean>
* 属性:
* value:指定bean的id。如果不指定value属性,默认bean的id是当前类的类名。首字母小写。
* */
@Component
public class UserServiceImpl implements UserService {
public void saveUser() {
System.out.println("saveUser方法执行了");
}
}
bean.xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd">
<!--开启IOC的注解开发包扫描-->
<context:component-scan base-package="com.zy.service"></context:component-scan>
</beans>
pom文件:
<dependencies>
<!--引入spring核心包-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.2.8.RELEASE</version>
</dependency>
</dependencies>
测试类:
public class TestIocAnno {
public static void main(String[] args) {
//加载配置文件
ApplicationContext context = new ClassPathXmlApplicationContext("bean.xml");
//根据bean标签的id获取实例
UserService bean = (UserService) context.getBean("userServiceImpl");
//调用方法
bean.saveUser();
}
}
运行结果:
2,@Autowired注解
2,@Autowired注解
作用:自动按照类型注入,当使用注解注入属性时,set方法可以省略。它只能注入其他 bean 类型。当有多个类型匹配时,使用要注入的对象变量名称作为 bean 的id,在 spring 容器查找,找到了也可以注入成功。找不到就报错。
我们在这个maven中添加一个dao层的接口和实现类,在service层注入dao层。
public interface UserDao {
/*
* 保存用户
* */
void saveUser();
}
/*
* dao接口实现类
* */
@Component
public class UserDaoImpl implements UserDao {
public void saveUser() {
System.out.println("dao保存用户成功...");
}
}
修改UserServiceImpl代码如下:
@Component
public class UserServiceImpl implements UserService {
@Autowired
private UserDaoImpl userDao;
public void saveUser() {
//调用dao层的方法
userDao.saveUser();
System.out.println("saveUser方法执行了");
}
}
运行测试类结果如下:
如果有两个相同类型的对象时我们使用@Autowired注解时,运行结果就会报错,例如下面代码:
@Repository(value = "userDao1")
public class UserDaoImpl implements UserDao {
public void saveUser() {
System.out.println("dao保存用户成功111...");
}
}
@Repository(value = "userDao2")
public class UserDaoImpl2 implements UserDao {
public void saveUser() {
System.out.println("dao保存用户成功222...");
}
}
运行测试类结果如下:
那该如何解决呢,我们要使用另外一个注解配合@Autowired一起使用。
3,@Qualifier注解
@Qualifier注解:
作用:在自动按照类型注入的基础之上,再按照 Bean 的 id 注入。它在给字段注入时不能独立使用,必须和 @Autowire 一起使用,但是给方法参数注入时,可以独立使用。
属性:value:指定 bean 的 id。
在service层实现类里面添加这个注解并通过value属性确定注入哪一个。
@Component
public class UserServiceImpl implements UserService {
@Autowired
@Qualifier(value = "userDao2")
private UserDao userDao;
public void saveUser() {
//调用dao层的方法
userDao.saveUser();
System.out.println("saveUser方法执行了");
}
}
然后运行测试类:
4,@Resource注解
如果我们不想使用@Autowired和@Qualifier注解一起使用,可以使用@Resource注解,该注解是直接按照 Bean 的 id 注入。它也只能注入其他 bean 类型,它也有name属性。
@Component
public class UserServiceImpl implements UserService {
// @Autowired
// @Qualifier(value = "userDao2")
@Resource(name = "userDao1")
private UserDao userDao;
public void saveUser() {
//调用dao层的方法
userDao.saveUser();
System.out.println("saveUser方法执行了");
}
}
4,@Value注解:
该注解的作用是注入基本数据类型和 String 类型的数据,属性:value:用于指定值 。可以使用spring中的SpEL表达式,${表达式}
5,@Scope注解: 作用:指定 bean 的作用范围。 属性:value:指定范围的值。值:singleton prototype,request,session,globalsession 。
@Service
@Scope(value = "singleton")
public class UserServiceImpl implements UserService {
......}
6,@PostConstruct 注解: 作用:用于指定初始化方法
@Service
@Scope(value = "singleton")
public class UserServiceImpl implements UserService {
// @Autowired
// @Qualifier(value = "userDao2")
@Resource(name = "userDao1")
private UserDao userDao;
@PostConstruct
public void init(){
System.out.println("初始化成功");
}
@PreDestroy
public void destroy(){
System.out.println("销毁成功");
}
public void saveUser() {
//调用dao层的方法
userDao.saveUser();
System.out.println("saveUser方法执行了");
}
}
7,@PreDestroy 注解: 作用:用于指定销毁方法。
@Service
@Scope(value = "singleton")
public class UserServiceImpl implements UserService {
// @Autowired
// @Qualifier(value = "userDao2")
@Resource(name = "userDao1")
private UserDao userDao;
@PostConstruct
public void init(){
System.out.println("初始化成功");
}
@PreDestroy
public void destroy(){
System.out.println("销毁成功");
}
public void saveUser() {
//调用dao层的方法
userDao.saveUser();
System.out.println("saveUser方法执行了");
}
}
加油吧少年