[000-01-010].第1节.Spring启示录

1.三层架构:

1.1.三层架构包括什么及职责:

  • 1.界面层(User Interface layer):
    • 主要功能是接受用户的数据,显示请求的处理结果。
    • 使用 web 页面和用户交互,手机 app 也就是表示层的,用户在 app 中操作,业务逻辑在服务器端处理。
  • 2.业务逻辑层(Business Logic Layer)
    • 接收表示传递过来的数据,检查数据,计算业务逻辑,调用数据访问层获取数据
  • 3.数据访问层(Data access layer):
    • 与数据库打交道。实现对数据的增、删、改、查。将存储在数据库中的数据提交给业务层,同时将业务层处理的数据保存到数据库.

1.2.三层架构对应的包

  • 1.界面层:controller包(servlet)
  • 2.业务逻辑层:service包(XXXService类)
  • 3.数据访问层:dao包(XXXDao类)

1.3.为什么要使用三层?

  • 1.结构清晰、耦合度低, 各层分工明确
  • 2.可维护性高,可扩展性高
  • 3.有利于标准化
  • 4.开发人员可以只关注整个结构中的其中某一层的功能实现
  • 5.有利于各层逻辑的复用

1.4.三层类中的交互

  • 1.用户使用界面层→业务逻辑层→数据访问层(持久层)→数据库(mysql)
    在这里插入图片描述
    在这里插入图片描述

1.5.三层架构对应的处理框架

  • 1.界面层–servlet–springmvc(框架)
  • 2.业务逻辑层–service类–spring(框架)
  • 3.数据访问层–dao类–mybatis(框架)

2.SSM框架介绍:

2.1.MyBatis 框架:

  • 1.MyBatis 是一个优秀的基于 java 的持久层框架,内部封装了 jdbc,开发者只需要关注 sql 语句本身,而不需要处理加载驱动、创建连接、创建 statement、关闭连接,资源等繁杂的过程;
  • 2.MyBatis 通过 xml 或注解两种方式将要执行的各种 sql 语句配置起来,并通过 java 对象和 sql 的动态参数进行映射生成最终执行的 sql 语句,最后由 mybatis 框架执行 sql 并将结果映射为 java 对象并返回;

2.2.Spring 框架:

a.概述:

  • 1.Spring 框架为了解决软件开发的复杂性而创建的。
  • 2.Spring 使用的是基本的 JavaBean 来完成以前非常复杂的企业级开发。Spring 解决了业务对象,功能模块之间的耦合,不仅在 javase,web 中使用, 大部分 Java 应用都可以从 Spring 中受益;
  • 3.Spring 是一个轻量级控制反转(IoC)和面向切面(AOP)的容器;

b.Spring 学习的核心内容:

  • 1.Spring 核心学习内容 IOC、AOP, jdbcTemplate, 声明式事务
    • IOC: 控制反转 , 管理 java 对象与对象之间的关系
    • AOP : 切面编程
    • JDBCTemplate : 是 spring 提供一套访问数据库的技术, 应用性强,相对好理解
    • 声明式事务: 基于 ioc/aop 实现事务管理
      在这里插入图片描述

2.3.SpringMVC 框架:

  • 1.Spring MVC 属于 SpringFrameWork 3.0 版本加入的一个模块,为 Spring 框架提供了构建 Web 应用程序的能力
  • 2.现在可以 Spring 框架提供的 SpringMVC 模块实现 web 应用开发,在 web 项目中可以无缝使用 Spring 和 Spring MVC 框架

3.传统开发模式分析:

3.1.案例1:

a.代码:

  • 1.UserController.java
package com.powernode.oa.controller;
import com.powernode.oa.service.UserService;
import com.powernode.oa.service.impl.UserServiceImpl;

public class UserController {
    private UserService userService = new UserServiceImpl();
    public void login(){
        String username = "admin";
        String password = "123456";
        boolean success = userService.login(username, password);
        if (success) {
            // 登录成功
        } else {
            // 登录失败
        }
    }
}
  • 2.UserServiceImpl.java
package com.powernode.oa.service.impl;

import com.powernode.oa.bean.User;
import com.powernode.oa.dao.UserDao;
import com.powernode.oa.dao.impl.UserDaoImplForMySQL;
import com.powernode.oa.service.UserService;

public class UserServiceImpl implements UserService {

    private UserDao userDao = new UserDaoImplForMySQL();

    public boolean login(String username, String password) {
        User user = userDao.selectByUsernameAndPassword(username, password);
        if (user != null) {
            return true;
        }
        return false;
    }
}
  • 3.UserDaoImplForMySQL.java
package com.powernode.oa.dao.impl;

import com.powernode.oa.bean.User;
import com.powernode.oa.dao.UserDao;

public class UserDaoImplForMySQL implements UserDao {
    public User selectByUsernameAndPassword(String username, String password) {
        // 连接MySQL数据库,根据用户名和密码查询用户信息
        return null;
    }
}

b.问题:

  • 1.可以看出:UserDaoImplForMySQL中主要是连接MySQL数据库进行操作。如果更换到Oracle数据库上,则需要再提供一个UserDaoImplForOracle.java,如下:
package com.powernode.oa.dao.impl;
import com.powernode.oa.bean.User;
import com.powernode.oa.dao.UserDao;

public class UserDaoImplForOracle implements UserDao {
    public User selectByUsernameAndPassword(String username, String password) {
        // 连接Oracle数据库,根据用户名和密码查询用户信息
        return null;
    }
}
  • 2.以上的操作正在进行功能的扩展,添加了一个新的类UserDaoImplForOracle来应付数据库的变化,这里的变化会引起连锁反应,如果想要切换到Oracle数据库上,UserServiceImpl类代码就需要修改,如下:UserServiceImpl.java
package com.powernode.oa.service.impl;

import com.powernode.oa.bean.User;
import com.powernode.oa.dao.UserDao;
import com.powernode.oa.dao.impl.UserDaoImplForOracle;
import com.powernode.oa.service.UserService;

public class UserServiceImpl implements UserService {

    //private UserDao userDao = new UserDaoImplForMySQL();
    private UserDao userDao = new UserDaoImplForOracle();

    public boolean login(String username, String password) {
        User user = userDao.selectByUsernameAndPassword(username, password);
        if (user != null) {
            return true;
        }
        return false;
    }
}

正常运行的代码,进行了修改,修改后影响了原有的代码模块,那么这就需要进行单元测试好多地方。这就违背了OCP开闭原则


3.2.案例2:传统Javaweb开发代码分析:

a.代码实现如下:

在这里插入图片描述

b.问题分析与解决:

b1.问题1与解决方式:
  • 1.问题1:层与层之间紧密耦合在一起,接口与具体实现紧密耦合在一起
    在这里插入图片描述
  • 2.解决办法:程序代码中不要手动new对象,第三方根据要求为程序提供需要的Bean对象
    在这里插入图片描述
b2.问题2分析与解决:
  • 1.问题2.通用的事务功能耦合在业务代码中通用的日志功能耦合在业务代码中:
    在这里插入图片描述
  • 2.解决方法:程序代码中不要手动new对象,第三方根据要求为程序提供需要的Bean对象的代理对象,代理对象内部动态结合业务和通用功能
    在这里插入图片描述

4.程序开发原则:

4.1.OCP开闭原则:

a.什么是OCP开闭原则:

  • 1.OCP开闭原则是软件设计中最基本的一个原则
    • 在软件开发过程中应当对扩展开放,
    • 对修改关闭

b.OCP开闭原则的核心:

  • 1.OCP开闭原则的核心是:
    • 在扩展系统功能的时候,没有修改之前写好的代码,这就符合OCP原则
    • 进行功能扩展的时候,添加额外的类是没问题的,但因为功能扩展而修改之前运行正常的程序,这是忌讳的,不被允许的。因为一旦修改之前运行正常的程序,就会导致项目整体要进行全方位的重新测试。这是相当麻烦的过程。

c.上述代码问题分析:

  • 1.根据上面案例2代码的变化:这样一来就违背了开闭原则OCP
    • 可以很明显的看出,上层是依赖下层的。UserController依赖UserServiceImpl,而UserServiceImpl依赖UserDaoImplForMySQL,这样就会导致下面只要改动,上面必然会受牵连(跟着也会改)
    • 所谓牵一发而动全身。这样也就同时违背了另一个开发原则:依赖倒置原则
  • 2.导致以上问题的主要原因是:代码和代码之间的耦合度太高。如下图所示:
    在这里插入图片描述

4.2.依赖倒置原则DIP:

a.依赖倒置原则概述:

  • 1.依赖倒置原则(Dependence Inversion Principle),简称DIP
    • DIP主要倡导面向抽象编程,面向接口编程,不要面向具体编程,让上层不再依赖下层,下面改动了,上面的代码不会受到牵连。
    • 依赖倒置的目的可以大大降低程序的耦合度,耦合度低了,扩展力就强了,同时代码复用性也会增强。(软件七大开发原则都是在为解耦合服务
  • 2.上面代码我们虽然可以看出是面向接口编程了,但是对象的创建new UserDaoImplForOracle()显然并没有完全面向接口编程,还是使用到了具体的接口实现类
    在这里插入图片描述

b.什么叫做完全面向接口编程?什么叫做完全符合依赖倒置原则呢?

  • 1.分析以下代码来看什么叫完全面向接口编程:
    在这里插入图片描述
  • 1.如果代码是这样编写的,才算是完全面向接口编程,才符合依赖倒置原则。那你可能会问,这样userDao是null,在执行的时候就会出现空指针异常呀。也确实是这样的,所以我们要解决这个问题。解决空指针异常的问题,其实就是解决两个核心的问题:
    • 第一个问题:谁来负责对象的创建。【也就是说谁来:new UserDaoImplForOracle()/new UserDaoImplForMySQL()
    • 第二个问题:谁来负责把创建的对象赋到这个属性上。【也就是说谁来把上面创建的对象赋给userDao属性
  • 2.如果我们把以上两个核心问题解决了,就可以做到既符合OCP开闭原则,又符合依赖倒置原则。这些Spring框架可以做到。
    • 在Spring框架中,它可以帮助我们new对象,并且它还可以将new出来的对象赋到属性上
    • 换句话说,Spring框架可以帮助我们创建对象,并且可以帮助我们维护对象和对象之间的关系。比如:
      在这里插入图片描述
  • 3.Spring可以new出来UserDaoImplForMySQL对象,也可以new出来UserDaoImplForOracle对象,并且还可以让new出来的dao对象和service对象产生关系(产生关系其实本质上就是给属性赋值)。

如上这种思想将对象的创建权/管理权交出去了,不再使用硬编码的方式了。同时也把对象关系的管理权交出去了,也不再使用硬编码的方式了。像这种把对象的创建权交出去,把对象关系的管理权交出去,被称为控制反转

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值