Mybatis 的使用 (3) 关联表查询

1.关联查询

l  创建一个Customer类,Order类

public class Customer {
	private Integer id;
	private String name;
	private Integer age;	
	private Set<Order> orders;

	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 Integer getAge() {
		return age;
	}
	public void setAge(Integer age) {
		this.age = age;
	}
	public Set<Order> getOrders() {
		return orders;
	}
	public void setOrders(Set<Order> orders) {
		this.orders = orders;
	}
	@Override
	public String toString() {
		return "Customer [id=" + id + ", name=" + name + ", age=" + age + ", orders=" + orders + "]";
	}
}
package mybatis.entity;

public class Order {
	private Integer id;
	private String orderNumber;
	private Integer price;	
	private Customer customer;
		
	public Integer getId() {
		return id;
	}
	public void setId(Integer id) {
		this.id = id;
	}
	public String getOrderNumber() {
		return orderNumber;
	}
	public void setOrderNumber(String orderNumber) {
		this.orderNumber = orderNumber;
	}
	public Integer getPrice() {
		return price;
	}
	public void setPrice(Integer price) {
		this.price = price;
	}
	public Customer getCustomer() {
		return customer;
	}
	public void setCustomer(Customer customer) {
		this.customer = customer;
	}
	@Override
	public String toString() {
		return "Order [id=" + id + ", orderNumber=" + orderNumber + ", price=" + price + "]";
	}	
}

l  创建客户表和订单表

CREATE TABLE `t_customer` (
  `id` int(5) NOT NULL auto_increment,
  `name` varchar(20) default NULL,
  `age` int(2) default NULL,
  PRIMARY KEY  (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8
CREATE TABLE `t_order` (
  `id` int(5) NOT NULL auto_increment,
  `orderNumber` varchar(20) default NULL,
  `price` int(10) default NULL,
  `customer_id` int(5) default NULL,
  PRIMARY KEY  (`id`),
  KEY `customer_id` (`customer_id`),
  CONSTRAINT `t_order_ibfk_1` FOREIGN KEY (`customer_id`) REFERENCES `t_customer` (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8

1.1     根据id查询客户,关联查询订单

第一步:创建一个CustomerMapper.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="mybatis.entity.Customer">
	<resultMap type="Customer" id="customerWithOrder">
		<id property="id" column="id"/>
		<result property="name" column="name"/>
		<result property="age" column="age"/>
		<collection property="orders" ofType="Order">
			<!-- <id property="id" column="id"/> -->
			<id property="id" column="oid"/>
			<result property="orderNumber" column="orderNumber"/>
			<result property="price" column="price" />
		</collection>
	</resultMap>

	<!--可以正常的查出信息,但是由于返回类型的原因,订单信息无法封装到Customer中,解决办法如下:queryById2  -->
	<select id="queryById" resultType="Customer">
		select c.*, o.* from
		t_customer c left outer join t_order o on c.id=o.customer_id where
		c.id = #{id}
	</select>
	
	<!--两个个表的id同名,会造成一些错误,例如没有订单信息的会有一个空的订单记录,有多个订单信息得只能查出来一条,解决办法如下:queryById3  -->
	<select id="queryById2" resultMap="customerWithOrder">
		select c.*, o.* from
		t_customer c left outer join t_order o on c.id=o.customer_id where
		c.id = #{id}
	</select>
	<select id="queryById3" resultMap="customerWithOrder">
		select c.*, o.*,o.id as oid  from
		t_customer c left outer join t_order o on c.id=o.customer_id where
		c.id = #{id}
	</select>

</mapper>

第二步:将sql映射文件注册到sqlMapConfig.xml中(所有相关表已经包含进来,剩余相似步骤不提供文件了)

<?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>
	<typeAliases>
		<typeAlias type="mybatis.entity.User" alias="User"/>
		<typeAlias type="mybatis.entity.Book" alias="Book"/>
		<typeAlias type="mybatis.entity.Customer" alias="Customer"/>
		<typeAlias type="mybatis.entity.Order" alias="Order"/>
	</typeAliases>
	<environments default="development">
		<environment id="development">
			<transactionManager type="JDBC" />
			<dataSource type="POOLED">
				<property name="driver" value="com.mysql.jdbc.Driver" />
<!-- 				<property name="driver" value="com.mysql.jdbc.Driver" /> -->
				<property name="url" value="jdbc:mysql://127.0.0.1:3306/mybatis_demo" />
				<property name="username" value="root" />
				<property name="password" value="root" />
			</dataSource>
		</environment>
		
	</environments>
	<mappers>
		<mapper resource="mybatis/entity/UserMapper.xml"/>
		<mapper resource="mybatis/entity/BookMapper.xml"/>
		<mapper resource="mybatis/entity/CustomerMapper.xml"/>
		<mapper resource="mybatis/entity/OrderMapper.xml"/>
	</mappers>

</configuration>

第三步:使用mybatis提供的api,操作数据库

package mybatis;

import java.io.IOException;
import java.io.InputStream;
import java.util.List;

import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.Before;
import org.junit.Test;

import mybatis.entity.Customer;
import mybatis.entity.Order;

public class AssociationQueryTest {
	static final String CUSTOMER_NAMESPAC = "mybatis.entity.Customer";
	static final String ORDER_NAMESPAC = "mybatis.entity.Order";

	SqlSession sqlSession = null;

	@Before
	public void createSqlSesion() throws IOException {
		InputStream asStream = Resources.getResourceAsStream("mybatis-config.xml");
		SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(asStream);
		sqlSession = sqlSessionFactory.openSession();

	}

	// 根据Customer查询Order
	@Test
	public void testQuery() {
		List<Customer> customers = sqlSession.selectList(CUSTOMER_NAMESPAC + ".queryById", 1);
		for (Customer customer2 : customers) {
			System.out.println(customer2);
		}
		sqlSession.close();
	}

	@Test
	public void testQuery2() {
		Customer customer = sqlSession.selectOne(CUSTOMER_NAMESPAC + ".queryById2", 1);
		System.out.println(customer);
		sqlSession.close();
	}

	@Test
	public void testQuery3() {
		Customer customer = sqlSession.selectOne(CUSTOMER_NAMESPAC + ".queryById3", 1);
		System.out.println(customer);
		sqlSession.close();
	}


}

2.1     根据id查询订单,关联查询客户

第一步:创建一个OrderMapper.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="mybatis.entity.Order">

	<resultMap type="Order" id="orderColumns4Map">
		<id property="id" column="id" />
		<result property="orderNumber" column="orderNumber" />
		<result property="price" column="price" />
		<association property="customer" javaType="Customer">
			<id property="id" column="cid" />
			<result property="name" column="name" />
			<result property="age" column="age" />
		</association>
	</resultMap>

	<select id="queryById" resultMap="orderColumns4Map">
		select o.*,c.*,c.id as cid from t_order o
		left outer join t_customer c on o.customer_id=c.id where o.id=#{id}
	</select>


</mapper>

第二步:将sql映射文件注册到sqlMapConfig.xml中

第三步:使用框架提供的api操作数据库:

// 根据Order查询Customer
	@Test
	public void testQueryOrder() {
		 Order order = sqlSession.selectOne(ORDER_NAMESPAC+".queryById", 2);
		 System.out.println(order);
		 System.out.println(order.getCustomer());
		 sqlSession.close();
	}

3. 动态sql

3.1 查询

<select id="queryByCondition" resultType="User" parameterType="User">
		select
		<include refid="userColumns" />
		from t_user
		<!-- where 1=1 -->
		<where>
			<if test="id!=null">
				and id=#{id}
			</if>
			<if test="name!=null">
				and name=#{name}
			</if>
			<if test="age!=null">
				and age=#{age}
			</if>
		</where>
	</select>
@Test
	public void queryUserByCondition() {
		User user2 = new User();
		user2.setId(1);
		user2.setAge(23);
		user2.setName("张三");
		List<User> users = sqlSession.selectList(NAMESPACE + ".queryByCondition", user2);
		for (User user : users) {
			System.out.println(user);
		}
		sqlSession.close();
	}

3.2     更新

<!-- 有必要使用set标签,不然在进行属性是否为空的判断中容易因为‘,’出错 -->
	<update id="modifyByCondition" parameterType="User">
		update t_user
		<set>
			<if test="name!=null">
				name=#{name},
			</if>
			<if test="age!=null">
				age=#{age},
			</if>
			<if test="address!=null">
				address=#{address}
			</if>
		</set>
		where id=#{id}
	</update>
@Test
	public void modifyUserByCondition() {
		User user2 = new User();
		user2.setId(1);
		user2.setAge(23);
		user2.setName("张三");
		int num = sqlSession.update(NAMESPACE + ".modifyByCondition", user2);
		System.out.println(num);
		sqlSession.close();
	}

4.  批量操作

4.1 批量插入数据

在sql映射文件中:

<insert id="insertDataList">
		insert into t_user
		(
		<include refid="userColumns" />
		)
		values
		<foreach collection="collection" item="user" separator=",">
			(null,#{user.name},#{user.age},#{user.address})
		</foreach>

	</insert>
@Test
	public void insertUserList() {
		Set<User> userSets = new HashSet<User>();
		for (int i = 0; i < 3; i++) {
			User user = new User("Name:"+i, 20+i, "北京:"+i);
			userSets.add(user);
		}
		int num = sqlSession.update(NAMESPACE + ".insertDataList", userSets);
		sqlSession.commit();
		System.out.println(num);
		sqlSession.close();
	}


4.2     根据id集合查询多条数据

Sql映射文件中:

<select id="queryInList" resultType="User">
		select
		<include refid="userColumns" />
		from t_user
		<if test="collection != null & collection.size() > 0">
			where id in
			<foreach collection="collection" item="user" separator="," open="(" close=")">
				#{user.id}
			</foreach>
		</if>
	</select>

@Test
	public void queryUserList() {
		Set<User> userSets = new HashSet<User>();
		for (int i = 1; i <=5; i++) {
			User user = new User();
			user.setId(i);
			userSets.add(user);
		}
		List<User> users= sqlSession.selectList(NAMESPACE + ".queryInList", userSets);
		for (User user : users) {
			System.out.println(user);
		}
		sqlSession.close();
	}









猜你喜欢

转载自blog.csdn.net/shangguanyunluo123/article/details/80368513
今日推荐