mybatis中多对多的步骤

示例:用户和角色,一个用户可以有多个角色,一个角色可以赋予多个用户

步骤:

  1. 建立两张表:用户表,角色表,让用户表和角色表具有多对多的关系,需要使用中间表,中间表中包含两张表的主键,在中间表中是外键
  2. 建立两个实体类:用户实体类和角色实体类,让用户和角色的实体类能体现出来多对多的关系,各自包含对方一个集合引用
  3. 建立两个配置文件,用户的配置文件,角色的配置文件
  4. 实现配置:当我们查询用户时,可以同时得到用户所包含的角色信息,当我们查询角色时,可以同时得到角色的所赋予的用户信息

数据库表的创立

实体类的建立

用户实体类

package com.itheima.domain;

import java.io.Serializable;
import java.util.Date;
import java.util.List; public class User implements Serializable { private Integer id;
private String username;
private String address;
private String sex;
private Date birthday; @Override
public String toString() {
return "User{" +
"id=" + id +
", username='" + username + '\'' +
", address='" + address + '\'' +
", sex='" + sex + '\'' +
", birthday=" + birthday +
'}';
} public Integer getId() {
return id;
} public void setId(Integer id) {
this.id = id;
} public String getUsername() {
return username;
} public void setUsername(String username) {
this.username = username;
} public String getAddress() {
return address;
} public void setAddress(String address) {
this.address = address;
} public String getSex() {
return sex;
} public void setSex(String sex) {
this.sex = sex;
} public Date getBirthday() {
return birthday;
} public void setBirthday(Date birthday) {
this.birthday = birthday;
}
}

角色实体类

package com.itheima.domain;

import java.io.Serializable;

public class Role implements Serializable {
private Integer roleId;
private String roleName;
private String roleDesc; public Integer getRoleId() {
return roleId;
} public void setRoleId(Integer roleId) {
this.roleId = roleId;
} public String getRoleName() {
return roleName;
} public void setRoleName(String roleName) {
this.roleName = roleName;
} public String getRoleDesc() {
return roleDesc;
} public void setRoleDesc(String roleDesc) {
this.roleDesc = roleDesc;
} @Override
public String toString() {
return "Role{" +
"roleId=" + roleId +
", roleName='" + roleName + '\'' +
", roleDesc='" + roleDesc + '\'' +
'}';
}
}

映射文件配置

用户映射文件

<?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.itheima.dao.IUserDao">
<!--定义User的resultMap-->
<resultMap id="userAccountMap" type="user">
<id property="id" column="id"></id>
<result property="username" column="username"></result>
<result property="address" column="address"></result>
<result property="sex" column="sex"></result>
<result property="birthday" column="birthday"></result>
</resultMap>
<!-- 查询所有 -->
<select id="findAll" resultMap="userAccountMap">
SELECT * FROM USER u LEFT OUTER JOIN account a ON u.id=a.uid;
</select> <!-- 根据id查询用户 -->
<select id="findById" parameterType="INT" resultType="user">
select * from user where id = #{uid}
</select>
</mapper>

角色映射文件

<?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.itheima.dao.IRoleDao">
<!--定义role表的ResultMap-->
<resultMap id="roleMap" type="role">
<id property="roleId" column="id"></id>
<result property="roleName" column="role_name"></result>
<result property="roleDesc" column="role_desc"></result>
</resultMap>
<!--查询所有-->
<select id="findAll" resultMap="roleMap">
select * from role;
</select>
</mapper>

测试类

package com.itheima.test;

import com.itheima.dao.IRoleDao;
import com.itheima.dao.IUserDao;
import com.itheima.domain.Role;
import com.itheima.domain.User;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test; import java.io.InputStream;
import java.util.List; /**
* @author 黑马程序员
* @Company http://www.ithiema.com
*
* 测试mybatis的crud操作
*/
public class RoleTest { private InputStream in;
private SqlSession sqlSession;
private IRoleDao roleDao; @Before//用于在测试方法执行之前执行
public void init()throws Exception{
//1.读取配置文件,生成字节输入流
in = Resources.getResourceAsStream("SqlMapConfig.xml");
//2.获取SqlSessionFactory
SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in);
//3.获取SqlSession对象
sqlSession = factory.openSession(true);
//4.获取dao的代理对象
roleDao = sqlSession.getMapper(IRoleDao.class);
} @After//用于在测试方法执行之后执行
public void destroy()throws Exception{
//提交事务
// sqlSession.commit();
//6.释放资源
sqlSession.close();
in.close();
} @Test
//查询所有账户,同时包含用户名称和地址
public void testFindAllAccountUser(){
List<Role> roles = roleDao.findAll();
for(Role role:roles){
System.out.println(role);
} } }

单表操作成功

实现配置:当我们查询角色时,可以同时得到角色的所赋予的用户信息

首先实体类需要添加一个属性

private List<User> users;

SQL语句的写法

SELECT u.*,r.id AS rid ,r.role_name,role_desc FROM role r
LEFT OUTER JOIN user_role ur ON r.id=ur.rid
LEFT OUTER JOIN USER u ON u.id = ur.uid;

有了SQL语句就可以写映射配置文件了

<?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.itheima.dao.IUserDao">
<!--定义User的resultMap-->
<resultMap id="userAccountMap" type="user">
<id property="id" column="id"></id>
<result property="username" column="username"></result>
<result property="address" column="address"></result>
<result property="sex" column="sex"></result>
<result property="birthday" column="birthday"></result>
</resultMap>
<!-- 查询所有 -->
<select id="findAll" resultMap="userAccountMap">
SELECT * FROM USER u LEFT OUTER JOIN account a ON u.id=a.uid;
</select> <!-- 根据id查询用户 -->
<select id="findById" parameterType="INT" resultType="user">
select * from user where id = #{uid}
</select>
</mapper>

实现配置:当我们查询用户时,可以同时得到用户所包含的角色信息,

SQL语句写法

SELECT u.*,r.id AS rid ,r.role_name,role_desc FROM USER u
LEFT OUTER JOIN user_role ur ON u.id=ur.uid
LEFT OUTER JOIN role r ON r.id = ur.rid;

JNDI

JNDI(Java Naming and Directory Interface Java命名和目录接口)是SUN公司提供的一种标准的Java命名系统接口。目的是模仿windows系统中的注册表

Mybatis中的延迟加载

问题:在一对多中,当我们有一个用户,他有100个账户。在查询用户的时候,要不要把关联的账户查出来?在查询账户的时候,要不要把关联的用户查出来?

在查询用户时,用户下的账户信息应该是,什么时候使用,什么时候加载。

在查询账户时,账户的所属用户信息应该是随着账户查询是一起查询出来。

什么是延迟加载:在真正使用数据时才发起查询,不用的时候不查询,按需加载(懒加载)0.

什么是立即加载:不管用不用,只要一调用方法,马上发起查询。

在对应的四种表关系中:一对多,多对多通常采用延迟加载,多对一,一对一:通常采用立即加载。

Mybatis中的缓存

什么是缓存:存在于内存中的 临时数据

一级缓存:指定是Mybatis中SqlSession对象的缓存,当我们执行查询后,查询的结果会同时存入到SqlSession为我们提供一块区域中,该区域的结构是一个map。当我们再次查询同样的数据,mybatis会先去sqlsession中查询是否有,有的话直接拿出来用,当SqlSession对象消失是,mybatis一级缓存也就消失了

二级缓存:它指的是Mybatis中SqlSessionFactory对象的 缓存,由同一个SqlSessionFactory对象创建的SqlSession共享其缓存

二级 缓存的使用步骤:

第一步:让Mybatis框架支持二级缓存(SqlMapConfig.xml中配置)

<settings>
<setting name="cacheEnabled" value="true"/>
</settings>

第二步:让当前的映射文件支持二级缓存(在IUserDao.xml中配置)

 <!--开启user支持二级缓存-->
<cache/>

第三步:让当前的操作支持二级缓存(select标签中配置)

    <!-- 根据id查询用户 -->
<select id="findById" parameterType="INT" resultType="user" useCache="true">
select * from user where id = #{uid}
</select>

test类

public void testFirstLevelCache(){
SqlSession sqlSession1 = factory.openSession();
IUserDao dao1 = sqlSession1.getMapper(IUserDao.class);
User user1 = dao1.findById(41);
System.out.println(user1);
sqlSession1.close();//一级缓存消失 SqlSession sqlSession2 = factory.openSession();
IUserDao dao2 = sqlSession2.getMapper(IUserDao.class);
User user2 = dao2.findById(41);
System.out.println(user2);
sqlSession2.close(); System.out.println(user1 == user2);
}

mybatis使用注解开发

package com.itheima.dao;

import com.itheima.domain.User;
import org.apache.ibatis.annotations.Select; import java.util.List;
//在mybatis中,有CRUD一共四个注解
//@Select @Insert @Update @Delete
public interface IUserDao {
//查询所有
@Select("select * from user")
List<User> findAll();
}

Mybatis笔记4的更多相关文章

  1. Mybatis笔记二:接口式编程

    目录 旧方法的弊端 接口式编程 接口式编程的好处 接口式编程的增删改查 旧方法的弊端 在Mybatis笔记一中,我们使用命名空间+id的方式实现了Mybatis的执行,不过这里的命名空间是我们随便写的 ...

  2. MyBatis笔记二:配置

    MyBatis笔记二:配置 1.全局配置 1.properites 这个配置主要是引入我们的 properites 配置文件的: <properties resource="db.pr ...

  3. MyBatis笔记一:GettingStart

    MyBatis笔记一:GettingStart 1.MyBatis优点 我们的工具和各种框架的作用就是为了我们操作数据库简洁,对于一些数据库的工具能帮我们少写一些处理异常等等的代码,但是他们并不是自动 ...

  4. 【MyBatis笔记】mapper文件的配置以及说明

    <!doctype html>[MyBatis笔记]mapper文件的配置以及说明 figure:last-child { margin-bottom: 0.5rem; } #write ...

  5. mybatis笔记2 基础理论准备

    之前发了一篇mybatis的crud入门笔记,算是入门了,为了让功力加深一级,来研究下mybatis的理论知识,哈哈,以后好拿来跟技术经理吹吹牛- 按照问题来吧!个人觉得有自主意识,带着自己的问题来研 ...

  6. mybatis笔记<二> 整合spring

    mybatis与spring整合需要添加几个jar包,mybatis-spring, spring-context, spring-jdbc 1. spring ioc只要一个jar包就ok 2. 我 ...

  7. mybatis笔记<一> Demo

    mybatis作为一个orm互联网公司基本都在用,今天写个笔记.记录一下mybatis使用 参考官网:http://www.mybatis.org/mybatis-3/getting-started. ...

  8. 【狂神说】JAVA Mybatis 笔记+源码

    简介 自学的[狂神JAVA]MyBatis GitHub源码: https://github.com/Donkequan/Mybatis-Study 分享自写源码和笔记 配置用的 jdk13.0.2 ...

  9. mybatis笔记3 一些原理的理解

    1,mybatis流程跟踪,原理理解 基本思路: 从SqlSessionFactory的初始化出发,观察资源的准备和环境的准备,以及实现持久层的一些过程: 进入SqlSessionFactoryBea ...

  10. mybatis笔记1 基本的配置和操作

    mybatis比较轻量,适合开发比较小型的或者业务比较复杂的系统: 相对于hibernate来说可以灵活的写sql,更灵活的处理遇到的业务逻辑: 可以说hibernate是pojo实体对db的orm映 ...

随机推荐

  1. (持续更新)vs2012,2013,2015,2017,2019 常用的插件 与 开发中常用的工具

    这篇博客 持续更新. 小伙伴们可以复制名称,在vs的扩展和更新中去搜索下载 .其他的工具在官网下载

  2. Latex 数字加粗后变宽 Latex bold without increasing the length of the text

    Add the following code at the beginning of the article \newsavebox\CBox \def\textBF#1{\sbox\CBox{#1} ...

  3. redis渐进式 rehash

    转载(http://redisbook.com/preview/dict/incremental_rehashing.html) 上一节说过, 扩展或收缩哈希表需要将 ht[0] 里面的所有键值对 r ...

  4. 2018-2019 20165226 Exp 8 Web基础

    2018-2019 20165226 Exp 8 Web基础 目录 一.实验内容说明及基础问题回答 二.实验过程 1.Web前端:HTML 2.Web前端j:avascipt 3.Web后端:MySQ ...

  5. 2019秋季 关于C语言指针等探索

    C语言指针探索 本篇博客由学生所写,如有错误之处,请在评论区留言 1.输出指针所储存的地址,使指针间接访问所储存地址的内容 #include <stdio.h> int main(void ...

  6. Java8 拼接字符串 StringJoiner

    StringJoiner1.简单的字符串拼接 输出:HelloWorld 注:当我们使用StringJoiner(CharSequence delimiter)初始化一个StringJoiner的时候 ...

  7. 【软工实践】Alpha冲刺(1/6)

    链接部分 队名:女生都队 组长博客: 博客链接 作业博客:博客链接 小组内容 恩泽(组长) 过去两天完成了哪些任务 描述 了解了反馈机制的实现原理 确定好算法的框架 对接口的规范化进行学习 展示Git ...

  8. 小程序运行报错navigateTo:fail page "pages/warn/warn" is not found

    在index.js中配置触发时页面转发 wx.navigateTo({ url: '../warn/warn', }) 实际上触发时报错页面找不到 原因是页面路径没有在app.json里面没有定义过, ...

  9. QEMU命令配置虚拟机网络的用户模式

    QEMU缺省使用“-net nic-net user”参数为客户机配置网络,提供了一种用户模式( user-mode)的网络模拟.使用用户模式的客户机可以连通宿主机及外部网络.用户模式网络完全由QEM ...

  10. 小D课堂 - 零基础入门SpringBoot2.X到实战_第2节 SpringBoot接口Http协议开发实战_6、SpringBoot2.xHTTP请求配置讲解

    1.SpringBoot2.xHTTP请求配置讲解 简介:SpringBoot2.xHTTP请求注解讲解和简化注解配置技巧 1.@RestController and @RequestMapping是 ...