mybatis小例子2

实现一对一,一对多查询

三个重点:1.resultmap 2.动态Sql 3.关联查询

创建工程,配置环境

  • 使用的工具是idea和MySQL,还有数据库的图形界面工具sqlyog,maven环境已经搭好前提下
  1. idea创建工程 maven.xxx.quickstart,添加模组maven.xxx.webapp,在对应pom.xml文件(小的)下<build></build> 标签和内容可以删除,因为maven已经自带了编译的功能不需要这个。
  2. 配置环境,在对应pom.xml的<dependencies></dependencies>标签中添加依赖
<!-- MySql -->
   <dependency>
     <groupId>mysql</groupId>
     <artifactId>mysql-connector-java</artifactId>
     <version>5.1.32</version>
   </dependency>
   <!-- Mybatis -->
   <dependency>
     <groupId>org.mybatis</groupId>
     <artifactId>mybatis</artifactId>
     <version>3.4.5</version>
   </dependency>
   <!--日志包-->
   <dependency>
     <groupId>org.slf4j</groupId>
     <artifactId>slf4j-log4j12</artifactId>
     <version>1.7.25</version>
   </dependency>
   <dependency>
     <groupId>log4j</groupId>
     <artifactId>log4j</artifactId>
     <version>1.2.17</version>
   </dependency>

访问数据库的四大信息

在资源文件夹下建一个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>
        <package name="com.wzx.bean"/>
    </typeAliases>

    <environments default="development">
        <environment id="development">

            <transactionManager type="JDBC"/>

            <dataSource type="POOLED">
                <!--    四大信息 -->
                <property name="driver" value="com.mysql.jdbc.Driver"/>
                <property name="url" value="jdbc:mysql://localhost:3306/(这里写数据库名)?characterEncoding=utf-8"/>
                <property name="username" value="root"/>
                <property name="password" value="123456"/>
            </dataSource>
        </environment>
    </environments>
<!--   一个mapper标签可以指定一个映射文件-->
    <mappers>

        <mapper resource="这里写要映射的子文件类似com/yzf/dao/UserDao.xml""/>
    </mappers>
</configuration>

SqlSession

是mybatis的核心,获取session对象对数据库访问,动态资源文件下创建对应类,也是访问数据库要的准备

public class MySessionUtils {

        private static SqlSessionFactory sessionFactory;
        //static 静态代码,在类加载的时候执行一次,且只执行一次
        static{
//  》1 创建SqlSessionFactoryBuilder对象
            SqlSessionFactoryBuilder sqlSessionFactoryBuilder = new SqlSessionFactoryBuilder();
// 》2 创建SqlSessionFactory对象
            InputStream inputStream = MySessionUtils.class.getClassLoader().getResourceAsStream("SqlMapConfig.xml");
            sessionFactory = sqlSessionFactoryBuilder.build(inputStream);//加载核心配置文件 参1 输入流
//        》3 加载SqlMapConfig.xml配置文件
        }
        public static SqlSession getSession() {
//        》4 创建SqlSession对象
            SqlSession sqlSession = sessionFactory.openSession();
            return sqlSession;
        }
    }

资源文件添加后缀.properties属性文件

# Global logging configuration
log4j.rootLogger=DEBUG, stdout
# Console output...
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%5p [%t] - %m%n

重点1.resultMap

resultMap标签映射关系和resultMap使用,在不改表不改类的情况下,字段名不一样的时候可以赋值。如果库里数据名和类名一样就可以不写<id colunmn="x" property="x"><result column="X" property="x"/>只要在type做好映射就好了。还有<association property="xx" javaType="xx"></association>标签可以自定义类型(重点3有例子),表连接查询能用到,property表示类名,javaType表示类的类型

<resultMap id="OrderMap" type="com.yzf.domain.Order">
        <!--        主键部份-->
        <id column="oid" property="oid"/>
        <!--        非主键部分-->
        <result column="(表名)" property="(类名)"/>
        <!--查询字段名与类的变量名一样的可以不写  -->
        <result column="number" property="number"/>
        <result column="createtime" property="createtime"/>
        <result column="note" property="note"/>
    </resultMap>
    <select id="findAll" resultMap="OrderMap">
        select * from tab_order
    </select>

测试使用。创建接口Dao类,测试里用getSession获取session,然后getMapper(xxx.class)(自动写方法实现sql语句),然后添加对应的方法名,添加xml文件,就是上面那部分代码修改一下。在最大的xml配置文件添加小的就行了。

重点2.动态Sql

有if标签,where和foreach等,最常用来高级搜索
例如select * from xx where xx like “xx” and xx = “xx”
有两个条件,如果想自由搜寻就适合用标签

 <select id="findByUser" resultType="com.yzf.domain.User">
        <where>
                <if test="username != null and username != '' ">
                and username like #{username}
                </if>
                <if test="address != null and address != '' ">
                and address = #{address}
                </if>
        </where>
    </select>

foreach标签,查询多个值的时候使用

<select id="findId" parameterType="list" resultType="com.yzf.domain.User">
       select * from userlist
       <where>
           <foreach collection="list" item="id" open="uid in(" close=")" separator=",">
           #{id}
           </foreach>
       </where>
   </select>

collection里的名字要对应接口的变量名,如果名字不一样可以在接口里添加@Param注解List<User> findId(@Param("ooo") List<Integer> list);item是遍历列表,集合元素赋值给item和python的循环差不多#{id}里面的id和item一样代表取每一个的值。open表示开始 close表示结束,separator代表分隔符。

重点3.关联查询,一对一

关系假设的是订单与用户关系,一个订单对应一个客户。(内连接inner join 左外连接 left outer join 右外连接right outer join 子查询select 嵌套 select)连接方便查看

  • 使用resultType方法返回值时,测试类里写下面的,对应接口写List<UserOrder> findAllUserOrder();
SqlSession session = MySessionUtils.getSession();
        OrderDao orderDao = session.getMapper(OrderDao.class);
        List<UserOrder> order = orderDao.findAllUserOrder();
        System.out.println(order);
        session.close();

对应的xml里写,要新建一个javaBean类保存数据,因为两个表连接了,数据数量对不上,用resultType必须有一个类对应全部的属性。

<select id="findAllUserOrder" resultType="com.yzf.domain.UserOrder">
        select * from tab_order o left join userlist u on o.user_id = u.uid
    </select>
  • 使用resultMap时,结合上面,在order类上面添加成员变量user,private User user,测试里写
   SqlSession session = MySessionUtils.getSession();

        OrderDao orderDao = session.getMapper(OrderDao.class);

        List<Order> list = orderDao.findAllUserOrder2();

        System.out.println(list);
        session.close();

这里写在OrderDao.xml,记得添加autoMapping=true,resultMap标签的type要设置好还有association中的property和javaType,查询方法一般一个个写不用*号,不写星号类似(select u.username from userlist u left join tab_order on u.id = o.id)userlist和tab_order是表名

<resultMap id="UserOrderMap" type="com.yzf.domain.Order" autoMapping="true" >
        <id property="oid" column="oid"></id>
       <association autoMapping="true" property="user" javaType="com.yzf.domain.User">

       </association>
    </resultMap>
    <select id="findAllUserOrder2" resultMap="UserOrderMap">
        select * from tab_order o left join userlist u on o.user_id = u.uid
    </select>

一对多查询

数据库select * from userlist u left join tab_order o on u.uid=o.user_id。在bean类User中定义List后面要用collection对应它private List<Order> orders;这是集合类型

  <resultMap id="UsersMap" type="com.yzf.domain.User" autoMapping="true">
           <id property="uid" column="uid"></id>
          <collection  property="orders" ofType="com.yzf.domain.Order" autoMapping="true">

          </collection>
       </resultMap>
       <select id="findAllUsers" resultMap="UsersMap">
           select * from userlist u left join tab_order o on u.uid=o.user_id
       </select>
  • 其中 < collection property=“order” javaType=“com.yzf.domain.Order”>中collection表示集合,property指定变量是定义那个变量名,ofType指里面的元素类型,记得是ofType
©️2020 CSDN 皮肤主题: 深蓝海洋 设计师:CSDN官方博客 返回首页