了解_MVC

MVC

MVC 设计模型(设计思想)

说明:在大型项目中由于模块众多,如果将所有项目都写到一起则代码特别混乱,不便于后期维护,所以通过MVC设计模型(设计思想),将代码进行分级,利于解耦

实现步骤:一般分3层,也可以分4层,5层,每层利用接口实现统一管理调用

  1. M(Model) 持久层 代码与数据库进行交互的代码 Mybatis dao层,还可加多Cao层
  2. C(Controller)控制层 完成某项业务的具体操作过程 Controller层 & Service层
  3. V (View)视图层 一般指用户看到的内容(页面)
    在这里插入图片描述

Spring容器管理3层代码结构

  1. 定义User POJO对象
package ink.pingdu.pojo;

public class User { //通过容器使用set方法为对象的属性赋值,所以必须有set方法
    private Integer id;
    private String name;

    public Integer getId() {
        return id;
    }

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

    public String getName() {
        return name;
    }

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

    @Override
    public String toString() {
        return "User{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }
}

  1. 在定义好的包dao下定义dao接口/实现类(说明:Spring内部)

Mybatis就是面向接口开发,所以在操作持久层时就写接口例:UserDao

UserDao接口

package ink.pingdu.dao;

import ink.pingdu.pojo.User;

public interface UserDao {

    /*要求调用者传一个User过来,从而实现add user.
      不过只有接口是无法干活的(无法add),所以必须要有实现类*/
    void addUser(User user);
}

UserDaoImpl 实现类

package ink.pingdu.dao;

import ink.pingdu.pojo.User;

public class UserDaoImpl implements UserDao{

    //实现接口方法
    @Override
    public void addUser(User user) {
        //下面为伪代码,实现开发中是需要链接数据库并执行SQL
        System.out.println("链接数据库执行 insert into:"+user); 
    }
}
  1. 在定义好的service包下定义Service接口/实现类

UserService 接口

package ink.pingdu.service;

import ink.pingdu.pojo.User;

public interface UserService {
    void addUser(User user);
}

UserServiceImpl 实现类

package ink.pingdu.service;

import ink.pingdu.dao.UserDao;
import ink.pingdu.dao.UserDaoImpl;
import ink.pingdu.pojo.User;

public class UserServiceImpl implements UserService{

    //三层代码总之是有关联才能贯通,需要调用持久层的东西,所以需要调用Dao层
//    private UserDao userDao = new UserDaoImpl();//早期只能new它的实现类来调用它的方法

    private UserDao userDao;    //基于Spring注入Dao 面向接口编程,写的是接口,实现注入的是实现类

    //Spring中通过DI(依赖注入):使用Set方法为属性赋值
    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }

    @Override
    public void addUser(User user) { //别人传给UserServiceImpl的user要传给userDao
        //加工就是Service层的必要性,例:
        String name = user.getName()+"加工数据"; // name就是加工后的数据
        user.setName(name); //存入加工后的数据

        userDao.addUser(user);  //接收UserServiceImpl的加工后的user,并入库操作
    }
}
  1. 在Controller包下定义UserController
package ink.pingdu.controller;

import ink.pingdu.pojo.User;
import ink.pingdu.service.UserService;

/**
 * 实现类,不写成接口的原因:
 * controller为顶层的,不需要被别的类调用,都是自己调用自己,
 * 不需要写成接口,因为接口是为了被别人类调用。
 */
public class UserController {

    /*controller层不可能单独实现读写数据库,所以需要根据结构化的层
      级代码调用service层
    */
    private UserService userService; //Spring容器负责注入service对象
    private User user; //暂代替用户传入的数据,本来是由前端传入

    //IOC 通过Set注入对象
    public void setUserService(UserService userService) {
        this.userService = userService;
    }
    public void setUser(User user) {
        this.user = user;
    }

    public void addUser(){
        userService.addUser(user);     //传入的 user,Spring注入的(见属性)
    }
}
  1. 编辑xml配置文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       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">

    <!--1、构建user对象,POJO对象是用来封装业务属性的,该对象通过Di注入要传给Controller,然后一直传到DAO层并写入数据库-->
    <bean id="user" class="ink.pingdu.pojo.User">
        <property name="id" value="100"></property>
        <property name="name" value="springMVC设计模式"></property>
    </bean>

    <!--2、构建Dao对象(与User对象不能有关系,本对象没有话语权,数据是由service传过来,所以上层还得构建Service与自己关联)
            根据面向接口编程书写规范:Id 必须写接口的名称 class 必须写实现类的包路径-->
    <bean id="userDao" class="ink.pingdu.dao.UserDaoImpl"></bean>

    <!--3、构建Service(要把数据传递给Dao,所以在Service中需要Dao对象,所以Spring会通过Set方法给Service注入Dao对象)
            书写规范同Dao
            但是要注意:因为Service要与Dao有关联所以Service就会有一个Dao,做为Service的属性,有属性就得为它赋值
            因为赋的不是一个具体的值,而是要赋予的是一个UserDao对象,所以不用Value,而是用ref(引用)-->
    <bean id="useService" class="ink.pingdu.service.UserServiceImpl">
        <property name="userDao" ref="userDao"></property>
    </bean>

    <!--4、构建Controller(User对象本来是由前端传入,但是本次测试我们自己给User赋值,User对象注入给Controller后
            把数据传下去,一直传到Dao层,写入数据库。)
        注意:编写规范一样。另该类有两个属性需要注入
        -->
    <bean id="userController" class="ink.pingdu.controller.UserController">
        <property name="userService" ref="useService"></property>
        <property name="user" ref="user"></property>
    </bean>

</beans>
  1. 编辑测试类
package ink.pingdu;

import ink.pingdu.controller.UserController;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestSpring {

    @Test
    public void testSpringMVC(){
        ApplicationContext context=new ClassPathXmlApplicationContext("application.xml");
        //注意:调程序,从Controller开始
        UserController userController = (UserController) context.getBean("userController");
        userController.addUser();
        System.out.println("恭喜学会MVC结构");
    }
}

补充:

三层代码结构关联 (目的:为了松耦合)
**MVC**
* Controller:为了接收用户提交的参数
* Service: 为了对数据进行业务处理(数据处理后是在内存中,线程执行完后内存资源就释放了,数据就会丢失。
* Dao (官方叫: Mapper):为了对数据进行持久化操作

Controller想addUser ,所以Service也为它准备了addUser,此时Controller与Service根本没有关联,那Controller想调用Service的addUser方法,就必须把UserService对象传给Controller,此时如果是new Service那就不是松耦合了,所以Spring通过DI(set方法注入),获得了userService对象,那自然可以用它的方法 service.addUser(),Service中间层做业务处理完后要想把数据入库,需要Dao层帮助,因为是同一个业务,所以Dao也为Service准备了addUser方法,Service要想调用Dao的方法,所以Service层也得注入Dao对象(userDao),获取到UserDao,也就可以调用其方法addUser,程序运行到Dao层,Dao运行其内部的addUser()实现数据写入数据库。<注意:调用接口时,其实现类必然会执行>

图示红箭头为程序运行顺序
在这里插入图片描述
补充说明:
如果从Controller --> Service --> Dao/Mapper 叫自上而下的开发方式,如果是从 Dao/Mapper --> Service --> Controller 叫自下而上的开发方式,初学阶段建议自下而上的方式开发,这样有利于理解。

关于特殊字符说明

原因:
由于业务需要xml配置文件中可能会有特殊字符,但是该特殊字符与xml关键字(标签)形成冲突。
解决方案:
实现字符串转义:

    <!--构建user对象,要显示为 <范冰冰> 冲突示范:-->
    <bean id="user" class="ink.pingdu.pojo.User">
        <property name="id" value="100"></property>
        <property name="name" value="<范冰冰>"></property>
    </bean>

    <!--正确示范一:
    	特殊转义字符:
			&lt; < 小于 
			&gt; > 大于  
			&amp; & 和号  
			&apos; ' 单引号  
			&quot; " 引号-->
    <bean id="user" class="ink.pingdu.pojo.User">
        <property name="id" value="100"></property>
        <property name="name" value="&lt;范冰冰&gt;"></property>
    </bean>
    
    <!--正确示范二:
        万能转义字符:<![CDATA[...任意字符]]>-->
    <bean id="user" class="ink.pingdu.pojo.User">
        <property name="id" value="100"></property>
        <property name="name">
            <value><![CDATA[<范冰冰>]]></value>
        </property>
    </bean>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值