平时我们都用JDBC访问数据库,除了需要自己写SQL之外,还必须操作Connection, Statement, ResultSet 这些其实只是手段的辅助类。 不仅如此,访问不同的表,还会写很多雷同的代码,显得繁琐和枯燥。
那么用了Mybatis之后,只需要自己提供SQL语句,其他的工作,诸如建立连接,Statement, JDBC相关异常处理等等都交给Mybatis去做了,那些重复性的工作Mybatis也给做掉了,我们只需要关注在增删改查等操作层面上,而把技术细节都封装在了我们看不见的地方。

HelloWorld编写

  1. 准备数据库和数据表,并导入相关数据
  2. 新建项目,并导入相关jar包
  3. 准备实体类,用于映射表。
    public class Category {
        private int id;
        private String name;
        public int getId() {
            return id;
        }
        public void setId(int id) {
            this.id = id;
        }
        public String getName() {
            return name;
        }
        public void setName(String name) {
            this.name = name;
        }
         
    }
  4. 配置实体类的文件Category.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.how2java.pojo">
            <select id="listCategory" resultType="Category">
                select * from   category_     
            </select>
        </mapper>
  5. 在src目录下创建mybatis的主配置文件mybatis-config.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.how2java.pojo"/>
        </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/how2java?characterEncoding=UTF-8"/>
                    <property name="username" value="root"/>
                    <property name="password" value="admin"/>
                </dataSource>
            </environment>
        </environments>
        <mappers>
            <mapper resource="com/how2java/pojo/Category.xml"/>
        </mappers>
    </configuration>
  6. 测试类
     
    public class TestMybatis {
     
        public static void main(String[] args) throws IOException {
            String resource = "mybatis-config.xml";
            InputStream inputStream = Resources.getResourceAsStream(resource);
            SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
            SqlSession session=sqlSessionFactory.openSession();
             
            List<Category> cs=session.selectList("listCategory");
            for (Category c : cs) {
                System.out.println(c.getName());
            }
             
        }
    }

对数据库的CRUD

配置文件Category.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.how2java.pojo">
        <insert id="addCategory" parameterType="Category" >
            insert into category_ ( name ) values (#{name})   
        </insert>
         
        <delete id="deleteCategory" parameterType="Category" >
            delete from category_ where id= #{id}  
        </delete>
         
        <select id="getCategory" parameterType="_int" resultType="Category">
            select * from   category_  where id= #{id}   
        </select>
 
        <update id="updateCategory" parameterType="Category" >
            update category_ set name=#{name} where id=#{id}   
        </update>
        <select id="listCategory" resultType="Category">
            select * from   category_     
        </select>    
    </mapper>

对应的CRUD代码:

增加
public class TestMybatis {
 
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
 
        Category c = new Category();
        c.setName("新增加的Category");
        session.insert("addCategory",c);
         
        listAll(session);
         
        session.commit();
        session.close();
 
    }
 
    private static void listAll(SqlSession session) {
        List<Category> cs = session.selectList("listCategory");
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}
删除:
public class TestMybatis {
 
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
 
        Category c = new Category();
        c.setId(6);
        session.delete("deleteCategory",c);
         
        listAll(session);
         
        session.commit();
        session.close();
 
    }
 
    private static void listAll(SqlSession session) {
        List<Category> cs = session.selectList("listCategory");
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}
获取:
public class TestMybatis {
 
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
 
        Category c= session.selectOne("getCategory",3);
         
        System.out.println(c.getName());
         
//      listAll(session);
         
        session.commit();
        session.close();
 
    }
 
    private static void listAll(SqlSession session) {
        List<Category> cs = session.selectList("listCategory");
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}
修改:
public class TestMybatis {
 
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
 
        Category c= session.selectOne("getCategory",3);
        c.setName("修改了的Category名稱");
        session.update("updateCategory",c);
         
        listAll(session);
         
        session.commit();
        session.close();
 
    }
 
    private static void listAll(SqlSession session) {
        List<Category> cs = session.selectList("listCategory");
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}
查询所有:
public class TestMybatis {
 
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
 
        listAll(session);
         
        session.commit();
        session.close();
 
    }
 
    private static void listAll(SqlSession session) {
        List<Category> cs = session.selectList("listCategory");
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}

其他查询:

模糊查询:因为是多个参数,而selectList方法又只接受一个参数对象,所以需要把多个参数放在Map里
<?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.how2java.pojo">
        <select id="listCategoryByName"  parameterType="string" resultType="Category">
            select * from   category_  where name like concat('%',#{0},'%')
        </select>    
    </mapper>
多条件查询:
<?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.how2java.pojo">
        <select id="listCategoryByName"  resultType="Category">
            select * from   category_  where name like concat('%',#{0},'%')
        </select>    
        <select id="listCategoryByIdAndName"  parameterType="map" resultType="Category">
            select * from   category_  where id> #{id}  and name like concat('%',#{name},'%')
        </select>    
    </mapper>
 Map<String,Object> params = new HashMap<>();
        params.put("id", 3);
        params.put("name", "cat");
        List<Category> cs = session.selectList("listCategoryByIdAndName",params);

一对多,多对一,多对多的关联

类----产品:一对多
pojo:类中添加一个list属性,存放产品
<?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.how2java.pojo">
        <resultMap type="Category" id="categoryBean">
            <id column="cid" property="id" />
            <result column="cname" property="name" />
     
            <!-- 一对多的关系 -->
            <!-- property: 指的是集合属性的值, ofType:指的是集合中元素的类型 -->
            <collection property="products" ofType="Product">
                <id column="pid" property="id" />
                <result column="pname" property="name" />
                <result column="price" property="price" />
            </collection>
        </resultMap>
     
        <!-- 关联查询分类和产品表 -->
        <select id="listCategory" resultMap="categoryBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname' from category_ c left join product_ p on c.id = p.cid
        </select>   
    </mapper>
产品------类:多对一
pojo:产品中添加一个类对象的引用。
<?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.how2java.pojo">
        <resultMap type="Product" id="productBean">
            <id column="pid" property="id" />
            <result column="pname" property="name" />
            <result column="price" property="price" />
     
            <!-- 多对一的关系 -->
            <!-- property: 指的是属性名称, javaType:指的是属性的类型 -->
            <association property="category" javaType="Category">
                <id column="cid" property="id"/>
                <result column="cname" property="name"/>
            </association>
        </resultMap>
     
        <!-- 根据id查询Product, 关联将Orders查询出来 -->
        <select id="listProduct" resultMap="productBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname' from category_ c left join product_ p on c.id = p.cid
        </select>   
    </mapper>

多对多(三张表)
order映射文件
<?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.how2java.pojo">
        <resultMap type="Order" id="orderBean">
            <id column="oid" property="id" />
            <result column="code" property="code" />
             
            <collection property="orderItems" ofType="OrderItem">
                <id column="oiid" property="id" />
                <result column="number" property="number" />
                <association property="product" javaType="Product">
                    <id column="pid" property="id"/>
                    <result column="pname" property="name"/>
                    <result column="price" property="price"/>
                </association>               
            </collection>
        </resultMap>
         
        <select id="listOrder" resultMap="orderBean">
            select o.*,p.*,oi.*, o.id 'oid', p.id 'pid', oi.id 'oiid', p.name 'pname'
                from order_ o
                left join order_item_ oi    on o.id =oi.oid
                left join product_ p on p.id = oi.pid
        </select>
             
        <select id="getOrder" resultMap="orderBean">
            select o.*,p.*,oi.*, o.id 'oid', p.id 'pid', oi.id 'oiid', p.name 'pname'
                from order_ o
                left join order_item_ oi on o.id =oi.oid
                left join product_ p on p.id = oi.pid
            where o.id = #{id}
        </select>
    </mapper>
product映射表:
<?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.how2java.pojo">
        <resultMap type="Product" id="productBean">
            <id column="pid" property="id" />
            <result column="pname" property="name" />
            <result column="price" property="price" />
     
            <!-- 多对一的关系 -->
            <!-- property: 指的是属性名称, javaType:指的是属性的类型 -->
            <association property="category" javaType="Category">
                <id column="cid" property="id"/>
                <result column="cname" property="name"/>
            </association>
        </resultMap>
 
        <select id="listProduct" resultMap="productBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname'
                from category_ c
                left join product_ p on c.id = p.cid
        </select>   
        <select id="getProduct" resultMap="productBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname'
                from category_ c
                left join product_ p on c.id = p.cid
            where p.id = #{id}
        </select>   
    </mapper>
中间表:
<?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.how2java.pojo">
     
        <insert id="addOrderItem" parameterType="OrderItem">
            insert into order_item_
                values(null,#{order.id},#{product.id},#{number})
        </insert>   
        <insert id="deleteOrderItem" parameterType="OrderItem">
            delete from order_item_
                where oid = #{order.id} and pid = #{product.id}
        </insert>   
     
    </mapper>

动态sql

执行不同的条件限定,需要准备不同的sql语句
如果Product的字段比较多的话,为了应付各个字段的查询,那么就需要写多条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.how2java.pojo">
        <select id="listProduct" resultType="Product">
            select * from product_
            <if test="name!=null">
                where name like concat('%',#{name},'%')
            </if>        
        </select>
         
    </mapper>
where标签<where>标签会进行自动判断
如果任何条件都不成立,那么就在sql语句里就不会出现where关键字
如果有任何条件成立,会自动去掉多出来的 and 或者 or。
set标签其效果与where标签类似,有数据的时候才进行设置。

注解方式表示取代xml方式:

mapper接口:
public interface CategoryMapper {
  
    @Insert(" insert into category_ ( name ) values (#{name}) ") 
    public int add(Category category); 
        
    @Delete(" delete from category_ where id= #{id} ") 
    public void delete(int id); 
        
    @Select("select * from category_ where id= #{id} ") 
    public Category get(int id); 
      
    @Update("update category_ set name=#{name} where id=#{id} ") 
    public int update(Category category);  
        
    @Select(" select * from category_ ") 
    public List<Category> list(); 
}
mybatis-config.xml增加对mapper接口的映射
<?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.how2java.pojo"/>
    </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/how2java?characterEncoding=UTF-8"/>
            <property name="username" value="root"/>
            <property name="password" value="admin"/>
            </dataSource>
        </environment>
    </environments>
    <mappers>
        <mapper resource="com/how2java/pojo/Category.xml"/>
        <mapper class="com.how2java.mapper.CategoryMapper"/> 
    </mappers>
</configuration>
测试类的增删改查
public class TestMybatis {
   
    public static void main(String[] args) throws IOException {
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
        SqlSession session = sqlSessionFactory.openSession();
        CategoryMapper mapper = session.getMapper(CategoryMapper.class);
  
//        add(mapper);
//        delete(mapper);
//        get(mapper);
//        update(mapper);
        listAll(mapper);
              
        session.commit();
        session.close();
   
    }
  
    private static void update(CategoryMapper mapper) {
        Category c= mapper.get(8);
        c.setName("修改了的Category名稱");
        mapper.update(c);
        listAll(mapper);
    }
  
    private static void get(CategoryMapper mapper) {
        Category c= mapper.get(8);
        System.out.println(c.getName());
    }
  
    private static void delete(CategoryMapper mapper) {
        mapper.delete(2);
        listAll(mapper);
    }
  
    private static void add(CategoryMapper mapper) {
        Category c = new Category();
        c.setName("新增加的Category");
        mapper.add(c);
        listAll(mapper);
    }
   
    private static void listAll(CategoryMapper mapper) {
        List<Category> cs = mapper.list();
        for (Category c : cs) {
            System.out.println(c.getName());
        }
    }
}