spring-IOC、DI

IOC控制反转是什么?

传统开发:开发者主动 new 创建对象、管理依赖;

控制反转:把对象的创建、生命周期管理、依赖装配交给 Spring 容器,控制权从代码转移到容器,所以叫反转。

IoC 容器里到底装了什么?(Bean 与 BeanFactory)

Spring 的 IoC 容器本质上是一个超级工厂,它里面装满了由 Spring 管理的 Java 对象,这些对象统称为 Bean。

容器的核心接口是:

  • BeanFactory:Spring 最底层的 IoC 容器,提供最基础的管理功能(延迟加载)。

  • ApplicationContext(应用上下文):它是 BeanFactory 的子接口,功能更强大(支持国际化、事件发布、AOP 集成等),我们在实际开发中用的就是它。

DI(Dependency Injection)依赖注入

在容器中建关系的整个过程是,称为依赖注入。

依赖注入它是实现 IoC 的一种主要方式。

例如:

复制代码
@Servicepublic class UserService {


    private final UserDao userDao;


    public UserService(UserDao userDao) {

        this.userDao = userDao;

    }

}

Spring 创建 UserService 时发现:

复制代码
UserService

      ↓

需要 UserDao

      ↓

IoC 容器查找 UserDao Bean

      ↓

创建/获取 UserDao

      ↓

注入 UserService

Spring 是怎么知道哪些对象需要管理的?

1. 注解扫描

例如:

复制代码
@Component
public class UserDao {

}


@Service
public class UserService {

}


@Controller
public class UserController {

}

Spring 启动时进行组件扫描,发现这些类以后,把它们注册到 IoC 容器。

2. @Bean

也可以手动注册:Spring 会把返回的对象放入 IoC 容器。

复制代码
@Configurationpublic class AppConfig {

    @Bean

    public UserService userService() {

        return new UserService();

    }

}

IoC 是怎么实现的?

Spring 主要通过 IoC 容器实现控制反转。项目启动时,Spring 会扫描 @Component、@Service、@Repository、@Controller 等组件,解析 Bean 定义并创建 Bean,保存到 IoC 容器中。当某个 Bean 依赖其他 Bean 时,Spring 根据依赖关系进行自动装配和注入,例如通过 @Autowired、@Resource 或构造器注入完成依赖关系建立。

复制代码
Spring 启动

    ↓

加载配置

    ↓

组件扫描

    ↓

找到 @Component、@Service 等组件

    ↓

解析 Bean 定义

    ↓

创建 Bean

    ↓

处理 Bean 依赖

    ↓

依赖注入

    ↓

初始化 Bean

    ↓

放入 IoC 容器

    ↓

业务代码获取并使用 Bean

降低耦合解析

没有 IoC 时(高耦合):

复制代码
public class UserService {

    // 自己主动 new 实现类,写死了

    private UserDao userDao = new MySqlUserDao();

    public void doSomething() {

        userDao.save();

    }

}

如果要把 MySqlUserDao 换成 OracleUserDao,必须修改 UserService 的源码。

使用 Spring IoC 后(低耦合):

复制代码
@Service
public class UserService {

    @Autowired // 由容器把合适的实现注入进来

    private UserDao userDao;

    public void doSomething() {

        userDao.save();

    }

}


@Repository
public class OracleUserDao implements UserDao { ... }

现在,UserService 只依赖 UserDao 接口。至于容器注入的是 MySqlUserDao 还是 OracleUserDao,完全由配置决定,UserService 的源码无需改动。

相关推荐
xcl092543 分钟前
宠物救助领养系统实战开发指南:从需求分析到部署上线
java·mfc·宠物
考虑考虑1 小时前
arthas使用
java·运维·后端
xcl09251 小时前
从零开发流浪宠物领养平台:技术选型与核心模块设计
java·spring boot·宠物
Dovis(誓平步青云)1 小时前
模拟器横评:电脑上看小说、追短剧用什么模拟器?MuMu、雷电、腾讯手游助手实测
android·java·服务器·前端·javascript·电脑
JienDa1 小时前
我做了一款不依赖 AI 的离线传统术数排盘工具:Electron、Vue3 与 Java 17 的完整实践
java·人工智能·electron
非凡ghost1 小时前
用 Kotlin 和 Jetpack Compose 重写的安卓视频播放器,原生体验有多流畅?
android·java·kotlin·音视频·软件需求
ttwosix1 小时前
JavaEE初阶 多线程 3
java·开发语言