一對一示例
一個妻子對應一個丈夫
數據庫表設計時 在妻子表中添加一個丈夫主鍵的作為外鍵
1 對應的JavaBean代碼
雖然在數據庫里只有一方配置的外鍵,但是這個一對一是雙向的關系。
Husband實體類
public class Husband implements Serializable{ private int hid; private String hname; private Wife wife; public int getHid() { return hid; } public void setHid(int hid) { this.hid = hid; } public String getHname() { return hname; } public void setHname(String hname) { this.hname = hname; } public Wife getWife() { return wife; } public void setWife(Wife wife) { this.wife = wife; } }
Wife 實體類
public class Wife implements Serializable{ private int wid; private String wname; private Husband husband; public int getWid() { return wid; } public void setWid(int wid) { this.wid = wid; } public String getWname() { return wname; } public void setWname(String wname) { this.wname = wname; } public Husband getHusband() { return husband; } public void setHusband(Husband husband) { this.husband = husband; } public Wife(int wid, String wname, Husband husband) { super(); this.wid = wid; this.wname = wname; this.husband = husband; } }
public interface HusbandMapper { //根據id查詢丈夫 public Husband queryHusbandById(int id); //根據id查詢丈夫和妻子 public Husband queryHusbandAndWife(int id); }
注意點 :雙向一對一關聯 有兩種配置文件的寫法
方式1:嵌套結果 使用嵌套結果映射來處理重復的聯合結果的子集 封裝聯表查詢的數據(去除重復的數據)
方式2:嵌套查詢 通過執行另外一個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.szjx.mapper.HusbandMapper"> <select id="queryHusbandById" resultType="Husband" parameterType="int"> select * from husband where hid=#{hid} </select> <!-- 查詢丈夫和妻子 雙向一對一的關系映射--> <!-- 兩種方式 1、 嵌套結果:使用嵌套結果映射來處理重復的聯合結果的子集 封裝聯表查詢的數據(去除重復的數據)--> <select id="queryHusbandAndWife" resultMap="husbandAndWife" parameterType="int"> select * from husband h left outer join wife w on h.wid=w.wid where h.hid=#{hid} </select> <!-- 一對一雙向關聯 兩種自定義返回集結果 --> <resultMap type="Husband" id="husbandAndWife"> <id property="hid" column="hid"/> <result property="hname" column="hname"/> <!--多表聯合查詢 必須要映射 不映射會報錯--> <association property="wife" javaType="Wife"> <id property="wid" column="wid"/> <result property="wname" column="wname"/> </association> </resultMap> <!-- 方式二:嵌套查詢:通過執行另外一個SQL映射語句來返回預期的復雜類型 SELECT * FROM class WHERE c_id=1; SELECT * FROM teacher WHERE t_id=1 //1 是上一個查詢得到的teacher_id的值 --> <select id="queryHusbandAndWife2" resultMap="husbandAndWife2" parameterType="int"> select * from husband where hid=#{hid} </select> <resultMap type="Husband" id="husbandAndWife2"> <id property="hid" column="hid"/> <result property="hname" column="hname"/> <association property="wife" javaType="Wife" select="getWife" column="wid"></association> </resultMap> <select id="getWife" resultType="Wife" parameterType="int"> select * from wife where wid=#{wid} </select> </mapper>
public class One2OneTest { private SqlSession sqlSession; private HusbandMapper mapper; @Before public void before(){ //獲取session sqlSession=DBTools.getSession(); mapper=sqlSession.getMapper(HusbandMapper.class); } @After public void after(){ //提交事務 sqlSession.commit(); } @Test public void queryHusband(){ Husband h=mapper.queryHusbandById(1);//根據id查詢丈夫 System.out.println(h); } @Test public void queryHusbandAndWife(){ Husband h=mapper.queryHusbandAndWife(1);//嵌套結果 System.out.println(h); } @Test public void queryHusbandAndWife2(){ Husband h=mapper.queryHusbandAndWife2(1);//嵌套查詢 System.out.println(h); } }
一對多
示例 : 一個人有 多個手機
1數據庫表的設計 手機表 作為 子表 有人 表 里的主鍵 作為外鍵
2 實體類的設計
Person
public class Person { private int pid; private String pname; private List<Phone> pList; public int getPid() { return pid; } public void setPid(int pid) { this.pid = pid; } public String getPname() { return pname; } public void setPname(String pname) { this.pname = pname; } public List<Phone> getpList() { return pList; } public void setpList(List<Phone> pList) { this.pList = pList; } }
Phone 類
public class Phone { private int tid; private String tname; private Person person; public int getTid() { return tid; } public void setTid(int tid) { this.tid = tid; } public String getTname() { return tname; } public void setTname(String tname) { this.tname = tname; } public Person getPerson() { return person; } public void setPerson(Person person) { this.person = person; } }
一對多 演示兩個操作 1批量操作 2查詢操作
1批量操作
定義 mapper接口 方法 和 xxxMapper.xml 映射文件
public interface PhoneMapper { //批量保存手機 public int batchSavePhone(@Param("phones") List<Phone> phones); }
PhoneMapper.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"> <mapper namespace="com.szjx.mapper.PhoneMapper"> <insert id="batchSavePhone"> insert into phone values <!-- 注意點 collection 的集合 是mapper接口中定義的@Param("phones")的值 ,兩個必須映射對應,否則就會報錯 --> <foreach collection="phones" item="phone" separator=","> <!--collection 為用於遍歷的元素(必選),支持數組、List、Set --> <!-- item 表示集合中每一個元素進行迭代時的別名. --> <!--separator表示在每次進行迭代之間以什么符號作為分隔 符. --> (null,#{phone.tname},#{phone.person.pid}) </foreach> </insert> </mapper>
4批量插入操作功能實現
public class One2ManyTest { private SqlSession sqlSession; private PhoneMapper mapper; @Before public void before(){ //獲取session sqlSession=DBTools.getSession(); mapper=sqlSession.getMapper(PhoneMapper.class); } @After public void after(){ //提交事務 sqlSession.commit(); } @Test public void batchSavePhone(){//批量保存數據 //在進行批量插入操作時 ,需要到 主表的主鍵 ,這時候可以將主表的數據從數據庫中查詢出來 在進行批量插入的操作 。 Person person=new Person();//這里就new一個對象作為主表對象 並設置主鍵的id person.setPid(1); List<Phone> phones=new ArrayList<>(); for(int i=0;i<10;i++){ Phone phone=new Phone(i,"ipone"+i,person); phones.add(phone); } System.out.println(phones); mapper.batchSavePhone(phones); } }
2一對多查詢功能的實現
3 定義 mapper接口 方法 和 xxxMapper.xml 映射文件
PersonMapper
public interface PersonMapper { //添加人 public int savePerson(Person person); //根據id查詢人的資料 public Person findPersonById(int id); //根據id查詢人與手機的資料 public Person findPersonAndPhone(int id);
PersonMapper.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"> <mapper namespace="com.szjx.mapper.PersonMapper"> <!-- 保存操作 --> <insert id="savePerson" parameterType="Person"> insert into person values(null,#{pname}) </insert> <!-- 根據ID查詢人員信息 返回值 類型是 Person類 --> <select id="findPersonById" parameterType="int" resultType="Person"> select * from person where pid=#{pid} </select> <!-- 根據id查詢人員和手機號 自定義返回結果集 --> <select id="findPersonAndPhone" parameterType="int" resultMap="personAndPhone"> select * from person p left outer join phone t on p.pid= t.pid where p.pid=#{pid} </select> <!-- 自定義返回結果集 方式1:嵌套結果 --> <resultMap type="Person" id="personAndPhone"> <id property="pid" column="pid"/> <result property="pname" column="pname"/> <!-- 注意點 集合的屬性值 :必須是實體類中 集合的成員變量名 --> <collection property="pList" ofType="Phone"> <id property="tid" column="tid"/> <result property="tname" column="tname"/> </collection> </resultMap> </mapper>
一對多查詢功能實現
public class One2ManyTest2 { private SqlSession sqlSession; private PersonMapper mapper; @Before public void before(){ //獲取session sqlSession=DBTools.getSession(); mapper=sqlSession.getMapper(PersonMapper.class); } @After public void after(){ //提交事務 sqlSession.commit(); } @Test public void findPersonById(){ //根據id查詢人員信息 Person person=mapper.findPersonById(1); System.out.println(person.getPname()); } @Test public void findPersonAndPhoneById(){ //根據id查詢人員和手機信息 Person person=mapper.findPersonAndPhone(1); System.out.println(person); } }