赞
踩
MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。
Mybatis通过SqlSessionFactoryBuilder来读取mybatis-config.xml配置文件从而创建SqlSessionFactory工厂类,SqlSessionFactory通过openSession方法来获取sqlSession,然后sqlSession通过getMapper来获取接口中的所有执行sql语句的方法。
优点:
缺点:
在数据库中可能会存在多对一的关系,比如说多个学生是一个班级、多个标签对一篇博客、多个学生对一个班主任等等。我们通常情况下创建的实体类中的属性是跟数据库里面的字段相对应,在一对多的环境下,实体类中的一个属性可以指向一个对象,然后通过Mybatis的ResultMap结果集映射,将相关联的表中的数据查找到后赋值给该属性,从而实现多对一的效果。
( 这里偷个懒,用lombok插件,添加依赖,通过注解添加构造器的方法 )
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class Student {
private int sid;
private String name;
private Class studentClass;
}
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class Class {
private int cid;
private String cname;
private String grade;
}
driver=com.mysql.cj.jdbc.Driver
url=jdbc:mysql://localhost:3306/mybatis?useUnicode=true&&characterEncoding=UTF-8&&useSSL=false&&serverTimezone=UTC
username=root
password=12345678
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <!--核心配置文件--> <configuration> <!-- properties:加载对应的配置文件 settings:配置Mybatis的一些设置,如:log4j日志信息等 typeAliases:扫描对应包下面的实体类,在xml文件中用小写表示就好 environments:配置数据库环境,可以配置多个,最后生效的为default transactionManager:声明事物管理器 mappers:扫描对应包下面的mapper.xml文件 --> <properties resource="db.properties" /> <!-- <settings>--> <!-- <setting name="logImpl" value="LOG4J"/>--> <!-- <setting name="cacheEnabled" value="true"/>--> <!-- </settings>--> <typeAliases> <package name="com.zhu.pojo" /> </typeAliases> <!--环境--> <environments default="development"> <environment id="development"> <transactionManager type="JDBC"/> <dataSource type="POOLED"> <property name="driver" value="${driver}"/> <property name="url" value="${url}"/> <property name="username" value="${username}"/> <property name="password" value="${password}"/> </dataSource> </environment> </environments> <mappers> <package name="com.zhu.mapper" /> </mappers> </configuration>
public class MybatisUtils { private static SqlSessionFactory sqlSessionFactory; static { try { String resources = "mybatis-config.xml"; InputStream in = Resources.getResourceAsStream(resources); sqlSessionFactory = new SqlSessionFactoryBuilder().build(in); } catch (IOException e) { e.printStackTrace(); } } public static SqlSession getSqlSession(){ return sqlSessionFactory.openSession(); } }
public interface StudentMapper {
//查找所有学生信息
List<Student> getStudent();
}
public interface ClassMapper {
//查询所有班级信息
List<Class> getStudentClass(@Param("cid") int cid);
}
方法一: 按照查询嵌套处理
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <!--核心配置文件--> <!--映射到对应的接口上--> <mapper namespace="com.zhu.mapper.StudentMapper"> <select id="getStudent" resultMap="getSClass"> select * from student; </select> <select id="getStudentClass" resultType="class"> select * from class where cid = #{cid} </select> <!-- property指的是实体类里面的属性名 column指的是要查询的字段 javaType表示实体类中属性的类型 select表示查询的方法 association:表示实体类对象,常用于多对一 这句话的意思就是根据学生的cid来查询对应的班级信息 --> <resultMap id="getSClass" type="student"> <association property="studentClass" column="cid" javaType="Class" select="getStudentClass" /> </resultMap> </mapper>
方法二: 按照结果嵌套处理
<mapper namespace="com.zhu.mapper.StudentMapper"> <select id="getStudent" resultMap="getSClass"> select a.*,b.* from student a,class b where a.cid=b.cid </select> <resultMap id="getSClass" type="student"> <result property="sid" column="sid" /> <result property="name" column="name" /> <association property="studentClass" javaType="class"> <result property="cid" column="cid" /> <result property="cname" column="cname" /> <result property="grade" column="grade" /> </association> </resultMap> </mapper>
测试代码:
public class TestMapper {
public static void main(String[] args) {
//通过工具类获取SqlSession
SqlSession sqlSession = MybatisUtils.getSqlSession();
StudentMapper mapper = sqlSession.getMapper(StudentMapper.class);
List<Student> students = mapper.getStudent();
for (Student student:students){
System.out.println(student);
}
}
}
测试结果:
将刚刚的实体类反过来一下,意思是一个班级对应多个学生、一个博客对应多个标签,一个班主任对应多个学生等等,将学生看作是一个集合,每个老师都有对应学生集合,也是通过Mybatis的ResultMap结果集映射,从而实现一对多的效果。
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class Student {
private int sid;
private String name;
private int cid;
}
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class Class {
private int cid;
private String cname;
private String grade;
private List<Student> students;
}
public interface StudentMapper {
//查找所有学生信息
List<Student> getStudent(@Param("cid") int cid);
}
public interface ClassMapper {
//查询所有班级信息
List<Class> getStudentClass();
}
方法一: 按照查询嵌套处理
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <!--核心配置文件--> <mapper namespace="com.zhu.mapper.ClassMapper"> <select id="getStudent" resultType="student"> select * from student where cid = #{cid} </select> <select id="getStudentClass" resultMap="StudentClass"> select * from class </select> <!-- collection:表示集合类对象,常用于一对多 ofType:表示返回的集合里面的泛型 这段sql语句的意思是通过查询出来的cid来查找对应班级的学生信息 --> <resultMap id="StudentClass" type="class"> <collection property="students" javaType="ArrayList" ofType="student" column="cid" select="getStudent" /> </resultMap> </mapper>
方法二: 按照结果嵌套查询
<mapper namespace="com.zhu.mapper.ClassMapper"> <select id="getStudentClass" resultMap="StudentClass"> select a.*,b.* from student a,class b where a.cid=b.cid; </select> <resultMap id="StudentClass" type="class"> <result property="cid" column="cid" /> <result property="cname" column="cname" /> <result property="grade" column="grade" /> <collection property="students" ofType="student"> <result property="sid" column="sid" /> <result property="name" column="name" /> <result property="cid" column="cid" /> </collection> </resultMap> </mapper>
将测试类里面的getMapper里面的参数变成ClassMapper.class,然后修改返回值,运行代码
测试结果:
多对多的处理其实也跟上面类似,可以看作是两个一对多,分别再两个实体类里面创建对应的集合或者实体类用于指向对方,然后分别再自己的Mapper.xml配置文件中实现两个一对多的处理即可,快结合上面的应用去实现一下吧!!!
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。