鉴别器:有时一个单独的数据库查询也许返回很多不同(但是希望有些关联)数据类型的结果集。鉴别器元素就是被设计来处理这个情况的,还有包括类的继承层次结构。[抄了一个定义,不是很理解,还是看例子吧]
1. 交通工具表vehicle
-
create table test.vehicle (
-
id bigint(10) primary key AUTO_INCREMENT,
-
vin varchar(10),
-
year date,
-
color varchar(10),
-
vendor varchar(10),
-
vehicle_type int, //类型:1表示car, 2表示boat
-
door_count int, //车门数量,car独有属性
-
quant varchar(10) //船桨,boat独有属性
-
);
2. java对应的实体类Vehicle,Car,Boat
-
package com.yjq.entity;
-
-
import java.sql.Date;
-
-
public class Vehicle {
-
-
private int id;
-
private String vin; //交通登记号码
-
private Date year;
-
private String color;
-
private String vendor;
-
private int vehicleType;
-
-
public Vehicle() {
-
}
-
-
public int getId() {
-
return id;
-
}
-
-
public void setId(int id) {
-
this.id = id;
-
}
-
-
public String getVin() {
-
return vin;
-
}
-
-
public void setVin(String vin) {
-
this.vin = vin;
-
}
-
-
public Date getYear() {
-
return year;
-
}
-
-
public void setYear(Date year) {
-
this.year = year;
-
}
-
-
public String getColor() {
-
return color;
-
}
-
-
public void setColor(String color) {
-
this.color = color;
-
}
-
-
public String getVendor() {
-
return vendor;
-
}
-
-
public void setVendor(String vendor) {
-
this.vendor = vendor;
-
}
-
-
public int getVehicleType() {
-
return vehicleType;
-
}
-
-
public void setVehicleType(int vehicleType) {
-
this.vehicleType = vehicleType;
-
}
-
-
}
package com.yjq.entity;
public class Car extends Vehicle { private int doorCount;
public Car() { }
public int getDoorCount() { return doorCount; }
public void setDoorCount(int doorCount) { this.doorCount = doorCount; } }
- <code class="language-java">package com.yjq.entity;
- public class Boat extends Vehicle {
- private String quant; //船桨
- public Boat() {
- }
- public String getQuant() {
- return quant;
- }
- public void setQuant(String quant) {
- this.quant = quant;
- }
- }</code>
3. 如何将查询结果映射为不同的对象呢?鉴别器登场
-
<?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.yjq.entity.Vehicle">
-
<resultMap id= "vehicleResult" type= "Vehicle">
-
<id property= "id" column= "id" />
-
<result property= "vin" column= "vin"/>
-
<result property= "year" column= "year"/>
-
<result property= "vendor" column= "vendor"/>
-
<result property= "color" column= "color"/>
-
<result property= "vehicleType" column= "vehicle_type"/>
-
<discriminator javaType= "int" column= "vehicle_type">
-
< case value= "1" resultMap= "carResult"/>
-
< case value= "2" resultMap= "boatResult"/>
-
</discriminator>
-
</resultMap>
-
<resultMap id= "carResult" type= "Car">
-
<result property= "vehicleType" column= "vehicle_type"/>
-
<result property= "doorCount" column= "door_count" />
-
</resultMap>
-
<resultMap id= "boatResult" type= "Boat">
-
<result property= "vehicleType" column= "vehicle_type"/>
-
<result property= "quant" column= "quant" />
-
</resultMap>
-
-
<select id= "selectVehicle" parameterType= "int" resultMap= "vehicleResult">
-
select * from vehicle where id =#{id};
-
</select>
-
</mapper>
4. 表中的数据
5. dao代码,看看查询效果
-
package com.yjq.dao;
-
-
import org.apache.ibatis.session.SqlSession;
-
-
import com.yjq.db.DbFactory;
-
import com.yjq.entity.Boat;
-
import com.yjq.entity.Car;
-
import com.yjq.entity.Vehicle;
-
-
public class VehicleDao {
-
-
public Vehicle selectVehicleById(int id) {
-
SqlSession session = DbFactory.getInstance().openSession();
-
Vehicle vehicle = (Vehicle) session.selectOne( "com.yjq.entity.Vehicle.selectVehicle", id);
-
session.commit();
-
session.close();
-
return vehicle;
-
}
-
-
public static void print(Vehicle v) {
-
if(v instanceof Car) {
-
Car c = (Car)v;
-
System.out.println( "Car: [id=" + c.getId() + ", vehicleType="
-
+ c.getVehicleType() + ", doorCount=" + c.getDoorCount() + "]");
-
} else if (v instanceof Boat) {
-
Boat b = (Boat)v;
-
System.out.println( "Boat: [id=" + b.getId() + ", vehicleType="
-
+ b.getVehicleType() + ", quant=" + b.getQuant() + "]");
-
} else {
-
System.out.println( "Vehicle: [id=" + v.getId() + ", vehicleType="
-
+ v.getVehicleType() + "]");
-
}
-
}
-
-
public static void main(String[] args) {
-
VehicleDao dao = new VehicleDao();
-
Vehicle v1 = dao.selectVehicleById( 1);
-
Vehicle v2 = dao.selectVehicleById( 2);
-
Vehicle v3 = dao.selectVehicleById( 3);
-
VehicleDao.print(v1);
-
VehicleDao.print(v2);
-
VehicleDao.print(v3);
-
}
-
-
}
-
//output
-
Car: [id= 1, vehicleType= 1, doorCount= 4]
-
Boat: [id= 2, vehicleType= 2, quant=lxj]
-
Vehicle: [id= 3, vehicleType= 3]
6. 蛋疼的地方
a) 重复配置:为了在Car,Boat,Vehicle类中能获取vehicleType属性,<result property="vehicleType" column="vehicle_type"/>配置了三次。
b) 多个resultMap:
i. 将查询语句的resultMap修改下,再看看输出:将所有的查询结果强行映射为Car了
-
<select id= "selectVehicle" parameterType= "int" resultMap= "carResult">
-
select * from vehicle where id =#{id};
-
</select>
-
//output
-
Car: [id= 1, vehicleType= 1, doorCount= 4]
-
Car: [id= 2, vehicleType= 2, doorCount= 0]
-
Car: [id= 3, vehicleType= 3, doorCount= 0]
7. 鉴别器的另外一种写法
-
<resultMap id= "vehicleResult" type= "Vehicle">
-
<id property= "id" column= "id" />
-
<result property= "vin" column= "vin"/>
-
<result property= "year" column= "year"/>
-
<result property= "vendor" column= "vendor"/>
-
<result property= "color" column= "color"/>
-
<result property= "vehicleType" column= "vehicle_type"/>
-
<discriminator javaType= "int" column= "vehicle_type">
-
< case value= "1" resultType= "Car">
-
<result property= "doorCount" column= "door_count" />
-
</ case>
-
< case value= "2" resultType= "Boat" >
-
<result property= "quant" column= "quant" />
-
</ case>
-
</discriminator>
-
</resultMap>
-