Many-to-many is not implemented in MyBatis, because many-to-many cascades can be replaced by two one-to-many cascades. In real life, one order can have multiple products, and one product can correspond to multiple orders. The relationship between orders and products is many-to-many. Similarly, one person can have multiple identities, and one identity can be owned by multiple people. If MyBatis wants to achieve many-to-many, it needs to use an intermediate table to convert the many-to-many into two one-to-many relationships. The cases in this article will use the relationship between people and identities to achieve many-to-many.
(1) Create database tables and intermediate tables.
CREATE TABLE `t_people` (
`pid` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(20) DEFAULT NULL,
`address` varchar(100) DEFAULT NULL,
PRIMARY KEY (`pid`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8;
INSERT INTO `t_people` VALUES (1,'tom','北京'),(2,'jerry','天津'),(3,'李承','湖南');
CREATE TABLE `t_role` (
`rid` int(11) NOT NULL AUTO_INCREMENT,
`act` varchar(20) DEFAULT NULL,
PRIMARY KEY (`rid`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8;
INSERT INTO `t_role` VALUES (1,'教师'),(2,'公务员'),(3,'大将军'),(4,'市长');
CREATE TABLE `t_peoplerole` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`pid` int(11) DEFAULT NULL,
`rid` int(11) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8;
INSERT INTO `t_peoplerole` VALUES (1,1,3),(2,2,2),(3,2,4),(4,3,3),(5,1,1),(6,1,4);
(2) Create People class and Role class
People class:
public class People {
private Integer id;
private String name;
private String address;
private List<Role> roleList;
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;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public List<Role> getRoleList() {
return roleList;
}
public void setRoleList(List<Role> roleList) {
this.roleList = roleList;
}
@Override
public String toString() {
return "People{" +
"id=" + id +
", name='" + name + '\'' +
", address='" + address + '\'' +
", roleList=" + roleList +
'}';
}
}
Role class:
public class Role {
private Integer id;
private String act;
private List<People> peopleList;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getAct() {
return act;
}
public void setAct(String act) {
this.act = act;
}
public List<People> getPeopleList() {
return peopleList;
}
public void setPeopleList(List<People> peopleList) {
this.peopleList = peopleList;
}
@Override
public String toString() {
return "Role{" +
"id=" + id +
", act='" + act + '\'' +
", peopleList=" + peopleList +
'}';
}
}
(3) Create the IPeopleDao class
public interface IPeopleDao {
List<People> findAllPeople();
}
(4) Create peopleMapper.xml
<?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">
<!--namespace:指定了唯一的命名空间-->
<mapper namespace="com.day1.dao.IPeopleDao">
<resultMap id="peopleRole" type="com.day1.entity.People">
<id property="id" column="pid"></id>
<result property="name" column="name"></result>
<result property="address" column="address"></result>
<collection property="roleList" ofType="com.day1.entity.Role" resultMap="role"></collection>
</resultMap>
<resultMap id="role" type="com.day1.entity.Role">
<id property="id" column="rid"></id>
<result property="act" column="act"></result>
</resultMap>
<select id="findAllPeople" resultMap="peopleRole">
select p.*, r.* from t_people p, t_role r, t_peoplerole pr where p.pid = pr.pid and pr.rid = r.rid;
</select>
</mapper>
(5) Configure the peopleMapper.xml file in SqlMapperConfig.xml
<mapper resource="com/day1/peopleMapper.xml"></mapper>
(6) Test
@Test
public void testSelect() throws IOException {
//1、读取配置文件
InputStream in = Resources.getResourceAsStream("SqlMapperConfig.xml");
//2、创建SqlSessionFactory工厂
SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder();
SqlSessionFactory factory = builder.build(in);
//3、使用工厂生产SqlSession对象
SqlSession sqlSession = factory.openSession();
//4、使用SqlSession创建dao接口的代理对象
IPeopleDao peopleDao= sqlSession.getMapper(IPeopleDao.class);
//5、使用代理对象执行方案
List<People> peopleList = peopleDao.findAllPeople();
for(People people : peopleList){
System.out.println(people);
}
//6、释放资源
sqlSession.close();
in.close();
}
Regarding the reason why only one piece of data appears in the many-to-many query or the problem caused by the same primary key names of the two tables I mentioned in the previous article (the primary key names of t_people and t_role are both id), this is a need to pay attention to The place. When the primary key names are inconsistent, this problem will not occur, that is, the primary key of t_people is pid, and the primary key of t_role is rid.