【Java笔记】Spring IoC & DI

[复制链接]
发表于 2025-7-4 17:43:15 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
Spring IoC & DI

Spring两个核心头脑:IoC & AOP
Spring相称于一个容器,IoC就是把对象存放在Spring容器中,让Spring帮我们管理对象,DI就是从Ioc容器中取出对象并注入给另一个对象,简言之,IoC就是存对象,DI就是取对象
1. IoC

注解:@Component,表示BookService这个对象已经交给Spring管理了,Spring帮我们new了一个对象
  1. @Component
  2. public class BookService {
  3.         ...
  4. }
复制代码
注解 :@Autowired表示从Spring容器中取出对象,赋值给bookService属性而且注入给BookController对象
  1. public class BookController {
  2.     @Autowired
  3.     private BookService bookService;
  4.         ...
  5. }
复制代码
1.1 Bean的存储

   两类注解:
  

  • 类注解 - 五大注解:@Controller @Service @Repository @Component @Configuration
  • 方法注解:@Bean
  1.1.1 类注解

  1. @Controller
  2. public class UserController {
  3.     ...
  4. }
复制代码
  @SpringBootApplication在谁人类上,哪个类就是启动类
  ApplicationContext可以理解为Spring容器,Spring管理的对象都在这个容器中,需要从这里边拿到对象
通过 .getBean() 拿到对象,再执行对象中的方法,下代码示例是从ApplicationContext容器中获取对象的三种方法,三种方法获取到的是同一个对象:
  1. @SpringBootApplication
  2. public class SpringIocDemoApplication {
  3.     public static void main(String[] args) {
  4.         // 1. 通过类名获取对象
  5.         ApplicationContext context = SpringApplication.run(SpringIocDemoApplication.class, args);
  6.         UserController bean = context.getBean(UserController.class);
  7.         System.out.println(bean);
  8.         bean.sayHi();
  9.         // 2. 通过BeanName获得对象
  10.         UserController userController = (UserController)context.getBean("userController");
  11.         System.out.println(userController);
  12.         userController.sayHi();
  13.         // 3. 通过类名加类型获取对象
  14.         UserController userController1 = context.getBean("userController", UserController.class);
  15.         System.out.println(userController1);
  16.         userController1.sayHi();
  17.     }
  18. }
复制代码
  BeanName默认是类的小驼峰写法;当类名前两个字母都是大写时,BeanName就是类名
    五个注解都可以让Spring资助管理对象
  @Controller @Service @Repository @Configuration 都是 @Component 的衍生注解
  不同的注解的功能相同,但是表示的含义不同,雷同车牌号
  @Controller定位最清晰,表示接收哀求的类通常使用@Controller或@RestController注解,不推荐使用其他注解(如@Service、@Repository等)
  

  • @Controller :对应三层架构的体现层
  • @Service:对应业务逻辑层
  • @Repository:对应数据层
  • @Configuration:表示设置层
  • @Component:表示组件
1.1.2 方法注解 @Bean

@Bean必须搭配五大注解使用,因为如果类都没有交给Spring管理,那么方法是不会在Spring容器中找到的,一般搭配@Configuration @Component都可以
将第三方的方法交给Spring管理使用@Bean
@Bean注解定义的bean,beanName为方法名,不是类的小驼峰写法了
同一个类型有多个bean只能通过以下的两种方式获取对象,需要加上beanName:
  1. UserInfo bean = context.getBean("user1",UserInfo.class);
  2. System.out.println(bean);
  3. UserInfo bean2 = context.getBean("user2",UserInfo.class);
  4. System.out.println(bean2);
复制代码
1.1.3 重定名

五大注解的beanName重定名:
  1. @Repository("ur")
  2. public class UserRepository {
  3.     public void doRepository() {
  4.         ...
  5.     }
  6. }
复制代码
  1. UserRepository bean = context.getBean("ur", UserRepository.class);
  2. bean.doRepository();
复制代码
@Bean的beanName重定名:
  1. @Bean(name = "zhangsan")
  2. public UserInfo user1() {
  3.     UserInfo userInfo = new UserInfo(1, "zhangsan", 12);
  4.     return userInfo;
  5. }
复制代码
  1. UserInfo bean = context.getBean("zhangsan",UserInfo.class);
复制代码
也可以有多个重定名:
  1. @Bean(name = {"user1", "zhangsan"})
复制代码
1.1.4 Spring扫描路径

启动类所在的路径就是默认的扫描路径,也可以通过在类上加注解@ComponentScan(basePackages = “路径”)指定扫描路径。
2. DI

DI就是依靠注入;
   Spring依靠注入的三种方式:
  

  • 属性注入:使用注解@Autowired


    • 构造方法注入:如果只有一个构造方法,@Autowired可以省略(Spring 4.3+版本);
    • 如果存在多个构造方法,如果无参的构造方法和有参的构造方法同时存在,默认使用无参的构造方法;如果要使用有参的构造方法,需要在有参的构造方法加上@Autowired。优先使用加@Autowired注解的构造方法,因为@Autowired优先级最高,没有@Autowired Spring就会找无参的构造方法,如果没有无参的构造方法会报错
    1.         private UserService userService;       
    2.       
    3.         public UserController2() {
    4.     }
    5.       
    6.     // 构造方法注入
    7.     @Autowired
    8.     public UserController2(UserService userService) {
    9.         this.userService = userService;
    10.     }
    复制代码
       

    • Setter注入
      setter方法也需要搭配@Autowired注解
    1. @Autowired
    2. public void setUserService(UserService userService) {
    3.     this.userService = userService;
    4. }
    复制代码

  步伐员通常使用属性注入的方式
当一个类中存在多个方法时,从这个类中取出方法需要使用:

  • @Primary指定默认的bean
  • @Qualifier(“beanName”)指定bean
  • 当@Primary、@Qualifier(“beanName”)同时存在使用@Qualifier(“beanName”)
  • 使用@Resource(name = “beanName”),作用等同于 @Qualifier(“beanName”) + @Autowired
   企业中更多使用的是@Resource(name = “beanName”) 和 @Autowired
  代码示例:
  1. //    @Autowired
  2. //    @Qualifier("user2")
  3.     @Resource(name = "user2")
  4.     private UserInfo userInfo;
复制代码
回复

使用道具 举报

登录后关闭弹窗

登录参与点评抽奖  加入IT实名职场社区
去登录
快速回复 返回顶部 返回列表