resultMap 主要是 mybatis 幫助從數據庫中獲取列數據后封裝成對象。
1 一對一映射
比如每位學生有一個地址。
public class Address { private Integer addrId; private String street; private String city; private String state; private String zip; private String country; // setters & getters } public class Student { private Integer studId; private String name; private String email; private PhoneNumber phone; private Address address; //setters & getters }
我們根據學生 ID 選擇學生信息
方法一:使用句點符號表示嵌套對象的引用,
Student 的 address 屬性使用了圓點記法被賦上了 address 對應列的值。
<resultMap type="Student" id="StudentWithAddressResult"> <id property="studId" column="stud_id" /> <result property="name" column="name" /> <result property="email" column="email" /> <result property="phone" column="phone" /> <result property="address.addrId" column="addr_id" /> <result property="address.street" column="street" /> <result property="address.city" column="city" /> <result property="address.state" column="state" /> <result property="address.zip" column="zip" /> <result property="address.country" column="country" /> </resultMap> <select id="selectStudentWithAddress" parameterType="int" resultMap="StudentWithAddressResult"> SELECT STUD_ID, NAME, EMAIL, A.ADDR_ID, STREET, CITY, STATE, ZIP, COUNTRY FROM STUDENTS S LEFT OUTER JOIN ADDRESSES A ON S.ADDR_ID=A.ADDR_ID WHERE STUD_ID=#{studId} </select>
方法二:使用mybatis提供的一對一映射,關鍵字:association
1)
<resultMap type="Address" id="AddressResult"> <id property="addrId" column="addr_id" /> <result property="street" column="street" /> <result property="city" column="city" /> <result property="state" column="state" /> <result property="zip" column="zip" /> <result property="country" column="country" /> </resultMap> <resultMap type="Student" id="StudentWithAddressResult"> <id property="studId" column="stud_id" /> <result property="name" column="name" /> <result property="email" column="email" /> <association property="address" resultMap="AddressResult" /> </resultMap> <select id="findStudentWithAddress" parameterType="int" resultMap="StudentWithAddressResult"> SELECT STUD_ID, NAME, EMAIL, A.ADDR_ID, STREET, CITY, STATE, ZIP, COUNTRY FROM STUDENTS S LEFT OUTER JOIN ADDRESSES A ON S.ADDR_ID=A.ADDR_ID WHERE STUD_ID=#{studId} </select>
元素<association>被用來導入“有一個”(has-one)類型的關聯。
如果內嵌的對象有對應的 resultMap 那么使用 <association property="address" resultMap="AddressResult" /> 比較方便。如果內嵌對象需要其它的查詢來生成對象,使用方法 3)比較好。
2)也可以使用<association 定義內聯的 resultMap,代碼如下所示:
<resultMap type="Student" id="StudentWithAddressResult"> <id property="studId" column="stud_id" /> <result property="name" column="name" /> <result property="email" column="email" /> <association property="address" javaType="Address"> <id property="addrId" column="addr_id" /> <result property="street" column="street" /> <result property="city" column="city" /> <result property="state" column="state" /> <result property="zip" column="zip" /> <result property="country" column="country" /> </association> </resultMap>
3)通過使用嵌套 select 查詢來獲取 Student 及其 Address 信息,代碼如下:
<resultMap type="Address" id="AddressResult"> <id property="addrId" column="addr_id" /> <result property="street" column="street" /> <result property="city" column="city" /> <result property="state" column="state" /> <result property="zip" column="zip" /> <result property="country" column="country" /> </resultMap> <select id="findAddressById" parameterType="int" resultMap="AddressResult"> SELECT * FROM ADDRESSES WHERE ADDR_ID=#{id} </select> <resultMap type="Student" id="StudentWithAddressResult"> <id property="studId" column="stud_id" /> <result property="name" column="name" /> <result property="email" column="email" /> <association property="address" column="addr_id" select="findAddressById" /> </resultMap> <select id="findStudentWithAddress" parameterType="int" resultMap="StudentWithAddressResult"> SELECT * FROM STUDENTS WHERE STUD_ID=#{Id} </select>
在此方式中,<association>元素的 select 屬性被設置成了 id 為 findAddressById 的語句。這里,兩個分開的SQL 語句將會在數據庫中執行,第一個調用 findStudentWithAddress 加載 student 信息,而第二個調用 findAddressById 來加載 address 信息。
Addr_id 列的值將會被作為輸入參數傳遞給 selectAddressById 語句;如果有多個參數可以通過逗號分隔。
2 一對多映射,關鍵詞使用 <collection>
比如老師和課程的關系,老師可以講多門課程,每門課程有一個老師
public class Course { private Integer courseId; private String name; private String description; private Date startDate; private Date endDate; private Integer tutorId; //setters & getters } public class Tutor { private Integer tutorId; private String name; private String email; private Address address; private List<Course> courses; // setters & getters }
1)使用內嵌結果 ResultMap 實現一對多映射。下面是配置文件
<resultMap type="Course" id="CourseResult"> <id column="course_id" property="courseId" /> <result column="name" property="name" /> <result column="description" property="description" /> <result column="start_date" property="startDate" /> <result column="end_date" property="endDate" /> </resultMap> <resultMap type="Tutor" id="TutorResult"> <id column="tutor_id" property="tutorId" /> <result column="tutor_name" property="name" /> <result column="email" property="email" /> <collection property="courses" resultMap="CourseResult" /> </resultMap> <select id="findTutorById" parameterType="int" resultMap="TutorResult"> SELECT T.TUTOR_ID, T.NAME AS TUTOR_NAME, EMAIL, C.COURSE_ID, C.NAME, DESCRIPTION, START_DATE, END_DATE FROM TUTORS T LEFT OUTER JOIN ADDRESSES A ON T.ADDR_ID=A.ADDR_ID LEFT OUTER JOIN COURSES C ON T.TUTOR_ID=C.TUTOR_ID WHERE T.TUTOR_ID=#{tutorId} </select>
<collection>元素的 resultMap 屬性設置成了 CourseResult,CourseResult 包含了 Course 對象屬性與表列名之間的映射。
2)使用嵌套 Select 語句實現一對多映射,配置文件如下
<resultMap type="Course" id="CourseResult"> <id column="course_id" property="courseId" /> <result column="name" property="name" /> <result column="description" property="description" /> <result column="start_date" property="startDate" /> <result column="end_date" property="endDate" /> </resultMap>
