Java 后端CH1 简单认识SSM和Redis
Ch1 简单认识SSM框架和Redis
写在前面:
JAVA后端的第一章只求先挖坑和入门,知道了大概有什么坑,以后再慢慢填坑,所以这一章主要整理这些框架的设计理念和技术特点。
参考资料:
1.《JaveEE 互联网轻量级框架整合开发 SSM框架和Redis实现》
目标:
-
了解对Spring IoC和AOP
-
了解什么是持久化以及持久化框架的作用
-
了解POJO、ORM
-
了解Hibernate和MyBatis的异同和各自适合场景
-
Spring MVC中,M、V、C分别是指什么
-
了解NoSQL是什么,与传统数据库的区别
-
了解Redis特性
一、Spring框架
Spring的两大成功理念及其特性:IoC(inversion of control控制反转)、AOP(aspect oriented programming 面向切面编程)
1.1 Spring IoC
- 什么是IoC,为什么要IoC及其优点?
IoC即控制反转,它是一个容器,将所有Java资源当作Java Bean,容器的目标是管理这些Bean和它们之间的关系。各个资源间也可能会有依赖关系,依赖关系也可以由IoC进行管理。Spring IoC是通过描述创建的(比如XML配置),而非人的主动创建,即控制反转。
如果不使用IoC,要完成用户对插座1选择与使用
|
Socket socket = new Socket1(); user.setSocket(socket); user.useSocket(); |
出现了Socket接口与Socket1的耦合
如果不使用IoC,要完成用户对插座2的选择与使用
|
Socket socket = new Socket2(); user.setSocket(sockey); user.useSocket(); |
出现了Socket接口与Socket2的耦合
若通过IoC,使用XML(Extensible mark language可扩展标记语言)来描述插座和用户
|
<bean id = "socket" class = "Socket1"/> <bean id = "user" class = "xxx.User"> <property name="socket" ref="socket"> </bean> |
即只需要更改第一句的class的值即可完成换用插座。
-
控制权在IoC容器中,它会根据使用者的描述找到使用者需要的资源,这就是控制反转。
1.2 Spring AOP
Ioc是为了管理Java Bean, 而Bean是Java面向对象的基础设计。
-
什么是AOP,与OOP的区别
AOP即面向切面编程,OOP在涉及多个对象之间协作时不够好,需要面向切面的编程,通过它来管理在切面上的某些对象之间的协作。
AOP常用于数据库事务的编程。如订单提交给生产部门,生产部门审批通过上报财务部门,而财务部门认为预算超支驳回生产申请,影响条件是预算超额,这是一个切面条件。很多时候,我们在做完第一步数据库的更新后,不知道下一步会不会成功,如果下一步失败,会使用数据库事务的功能回滚事务,使得第一步的数据库更新也作废。
-
简单说下AOP如何实现
AOP实现数据库事务管理中,是以异常作为消息的。默认情况下(可通过Spring的配置属性进行修改),异常会使数据库的事务回滚。
-
AOP举例,借例子说明AOP的优点
|
/** * Spring AOP 处理订单的伪代码 * @param order 订单 **/
Private void proceed(Order order){ boolean pflag = productionDept.isPass(order); if(pflag){ if(financialDept.isOverBudget(order)){ throw new RuntimeException("预算超额");//抛出异常,自动事务回滚 } } } |
优点:简单来说,没有复杂的try…catch…finally…,只需要关注有无异常。
二、 持久层框架(Hibernate和MyBatis)
2.1 用例子引入持久层框架的简单介绍
若数据库中有下表
|
角色表 |
|
编号 int(12) <pk> 角色名称 varchar(60) 备注 varchar(1024) |
根据这个角色表建立POJO(Plain Ordinary Java Object),和这张表的字段(属性、列)对应起来。
|
package com.learn.chapter1.pojo; public class Role implements java.io.serializable{ private Integer id; private String roleName; private String note; /** setter and getter **/ } |
持久层框架(无论是Hibernate还是MyBatis),都是依靠某种方法,将数据库的表和POJO映射起来的,这样程序员就可以操作POJO来完成相关的逻辑。
-
什么是持久化?
把内存的变成外存的,以及把外存的变成内存的过程叫做持久化。
2.2 Hibernate简介
在MyBatis或者Hibernete中可以通过XML或者注解提供映射规则,这里讨论的是XML方式,因为在MyBatis中注解方式会受到一定限制,所以MyBatis通常使用XML方式实现映射关系。
我们将POJO对象和数据库表相互映射的框架称为对象关系映射(Object Relational Mapping, ORM, O/RM, O/R mapping框架)。
Hibernate完全面向POJO,无需编写SQL。
Hibernate映射文件如下:
|
<?xml version="1.0"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD3.0//EN" "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping> <class name="com.learn.chapter1.pojo.Role" table="t_role"> <id name="id" type="java.lang.Integer"> <column name="id"/> <generator class="identity"/> </id> <property name="roleName" type="string"> <column name="role_name" length="60" not-null="true"/> </property> <property name="note" type="string"> <column name="note" length="512"/ > </property> </hibernate-mapping> |
映射配置后,就可以通过对POJO进行操作来影响t_role表中的数据,比如对其增、删、改、查。
|
Session session = null; Transation tx= null; try{ //打开session Session = HibernateUtil.getSessionFactory().openSession();
//事务 Tx = session.beginTransaction();
//POJO Role role = New Role(); role.setId(1); role.setRoleName("rolename1"); role.setNote("note1"); session.save(role); //保存
Role role2 = (Role) session.get(Role.class, 1); //查询 Role2.setNote("修改备注"); Session.update(role2); //更新 System.err.println(role2.getRoleName()); Session.delete(role2); //删除 Tx.commit(); //提交事务 } catch(Exception ex){ If(tx != null && tx.isActive()){ tx.rollback(); } ex.printStackTrace(); }finally { If(session != null && session.isOpen()){ session.close(); } } |
这里没看到SQL,是因为Hibernate会根据映射关系生成对应的SQL,程序员不需要精通SQL,只要懂得操作POJO即可操作对应数据库的表了。这在老的管理系统时代非常方便,可以快捷实现业务管理逻辑,所以Hibernate曾是那个时代的主流。
2.3 MyBatis简介
Mybatis与Hibernate最大的不同在于,它可以让程序员自己制定SQL规则,无须Hibernate自动生成规则,这样可以更精确定义SQL,从而优化性能,满足了这个时代高并发、大数据、高性能、高响应的要求。
与Hibernate一样,MyBatis也需要映射文件把POJO和数据库的表对应起来。
|
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.learn.chapter1.mapper.RoleMapper"> <resultMap id="roleMap" type="com.learn.chapter1.pojo.Role"> <id property="id" column="id"/> <result property="roleName" column="role_name" /> <result property="note" column="note"> </resultMap>
<select id="getRole" resultMap="roleMap"> select id, role_name, note from t_role where id = #{id} </select>
<delete id="deleteRole" parameterType="int"> delete from t_role where id = #{id} </delete>
<insert id="insertRole" parameterType="com.learn.chapter1.pojo.Role"> Insert into t_role(role_name, note) values (#{rolename}, #{note}) </insert>
<update id="updateRole" parameterType="com.learn.chapter1.pojo.Role"> update t_role set role_name = #{roleName}, note = #{note} where id = #{id} <update> </mapper> |
完成增删改查如下
|
SqlSession sqlSession = null; try{ sqlSession = MybatisUtil.getSqlSession(); RoleMapper roleMapper = sqlSession.getMapper(RoleMapper.class); Role role = roleMapper.getRole(1); //查询 System.err.println(role.getRoleName()); role.setRoleName("update_role_name"); roleMapper.updateRole(role);//插入 Role role2 = new Role(); role2.setNote("note2"); role2.setRoleName("role2"); roleMapper.insertRole(role); roleMapper.deleteRole(5);//删除 sqlSession.commit(); //提交事务 } catch (Exception ex){ ex.printStackTrace(); if(sqlSession != null){ sqlSession.rollback();//回滚事务 } } finally {//关闭连接 If(sqlSession != null){ sqlSession.close(); } } |
2.4 Hibernate与MyBatis的区别
-
简单来讲
对于业务逻辑层大同小异。
对于映射层,Hibernate不需要接口和SQL,而MyBatis需要。
-
详细点
对于Hibernate,不需要编写大量的SQL就可以完全映射,同时提供了日志、缓存、级联(级联比MyBatis 强大)等特性,此外还提供HQL(Hibernate Query Language)对POJO进行操作,使用非常方便,但它有很多致命缺陷。
Mybatis支持自由书写SQL,支持动态SQL、处理列表、动态生成表名、支持存储过程。这样就可以灵活地定义查询语句,满足各类需求和性能优化的需要,这在互联网系统中非常关键。
管理系统、ERP等对性能要求不高的系统推荐使用Hibernate
对性能要求高、响应快、灵活的系统则推荐使用MyBatis。
三、Spring MVC
曾经,Struts2与Spring的结合存在着兼容性和类臃肿的问题,加上这几年struts2的漏洞问题频发,导致使用率大减。
而Spring MVC结构层次清晰,类比较简洁,同时提供这些元素之间的松耦合。
-
Model(模型),封装了应用程序的数据和由它们组成的POJO,
-
View(视图),负责把模型数据渲染到视图上,将数据以一定形式展现给用户。
-
Controller(控制器),负责处理用户请求,并建立适当的模型把它传递给视图渲染。
在Spring MVC中还可以定义逻辑视图,通过其提供的视图解析器就能很方便地找到对应的视图进行渲染,或者使用其消息转换的功能,比如在Controller的方法内加入注解@ResponseBody后,Spring MVC就可以通过其消息转换系统,将数据转换为JSON,提供给前端Ajax使用。
Spring MVC的重点在于它的流程和一些注解,包括控制器、视图解析器、视图等重要内容。
四、 最流行的NoSQL——Redis
4.1 什么是Redis
Redis是一种NoSQL(Not only SQL),它具有一定持久层的功能也可以所为一种缓存工具。使用它可以显著提升互联网系统的性能。
对于常用数据,第一次从数据库读出,然后就存放在NoSQL中,这样以后就无须再访问数据库,只需从NoSQL中读出即可,性能就会比数据库快很多。对于那些高并发的操作,可以在NoSQL上先完成写入,等待某一时刻再批量写入数据库,这样就能满足系统的性能要求。
4.2 Redis与传统数据库区别
|
区别 |
Redis |
数据库 |
|
结构化程度 |
半结构化 |
结构化 |
|
数据完整性 |
低 |
高 |
|
性能及响应 |
高 |
低 |
|
操作原子性 |
所有操作都是原子性的 |
不一定 |
|
存储位置 |
内存 |
外存(硬盘等) |
4.3 Redis特性
-
响应快速:每秒执行110 000个写入操作,或者81 000个读操作,速度远远超过数据库,其速度远超数据库。如果存放一些常用的数据,就能有效提升系统的性能。
-
支持6种数据类型:字符串、哈希结构、列表、集合、可排序集合、基数。字符串可以存储一些Java基础数据结构,哈希可以存储对象,列表可以存储List对象等。虽然只有6种数据类型,但带来2个好处:1、已经满足存储各类数据结构体的需要;2、数据类型少,使得规则少,需要的判断和逻辑就少,这样读/写的速度就更快。
-
操作都是原子的:确保当两个客户同时访问时得到的都是最新的值。在需要高并发的场景下,可以考虑使用Redis的事务,处理一些需要锁的事务。
-
MultiUtility工具:Redis可以在如缓存、消息传递队列中使用(Redis支持"发布+订阅"的消息模式),在应用程序如Web应用程序会话、网站页面点击数等任何短暂的数据中使用.
五、 SSM+Redis结构框图和概述

(字老丑了)
-
IoC:资源管理、整合、即插即拔
-
AOP: 提供切面功能,特别是数据库事务管理的功能
-
Spring MVC: 提供数据库访问的持久层,通过MyBatis-Spring项目,它便能和Spring无缝对接。
-
MyBatis: 缓存工具,提供高速度处理数据和缓存数据的功能。使得系统大部分时候只需要访问缓存,而无须从数据库磁盘中重复读/写;在一些需要高速运算的场合,先拿它完成运算,再将数据批量放到数据库,可以提升系统性能和响应能力。
浙公网安备 33010602011771号