**什么是 MyBatis?**
MyBatis 是一个优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 避免了几乎所有的 JDBC 代码和手动设置参数以及获取结果集。
**MyBatis 的优点:**
1. **灵活性**: MyBatis 允许你直接编写 SQL 语句,这使得它非常灵活。
2. **简单易学**: MyBatis 相比于全自动 ORM 框架,如 Hibernate,学习曲线较低。
3. **性能高**: 由于直接执行 SQL,MyBatis 的性能通常比全自动 ORM 框架高。
4. **数据库无关**: MyBatis 可以与任何数据库一起使用。
5. **动态 SQL**: 支持通过 XML 或注解编写动态 SQL。
**MyBatis 框架的缺点:**
1. **代码量大**: 需要手动编写 SQL 语句,导致代码量较大。
2. **SQL 维护成本高**: SQL 语句嵌入在代码中,维护成本较高。
3. **数据库移植性差**: 由于直接使用 SQL,不同数据库之间的 SQL 语法差异可能导致移植困难。
**MyBatis 框架适用场合:**
1. **对 SQL 有严格控制需求的项目**: 需要精确控制 SQL 执行的情况。
2. **复杂查询操作**: 需要复杂的 SQL 查询或存储过程的场景。
3. **对性能有高要求的项目**: 需要高性能数据库操作的情况。
**MyBatis 与 Hibernate 的不同:**
1. **SQL 控制**: MyBatis 需要手动编写 SQL,Hibernate 自动生成 SQL。
2. **缓存机制**: Hibernate 提供更丰富的缓存机制,而 MyBatis 主要依赖手动控制。
3. **学习曲线**: Hibernate 的学习曲线比 MyBatis 陡峭。
4. **适用场景**: Hibernate 更适合于数据表结构变化频繁的项目,而 MyBatis 更适合于 SQL 复杂且变化少的项目。
**#和 $的区别:**
- **#{}**: 预编译语句,占位符,防止 SQL 注入。
- **${}**: 直接拼接字符串,存在 SQL 注入风险。
**当实体类中的属性名和表中的字段名不一样怎么办?**
使用 MyBatis 的 `<resultMap>` 元素进行属性和字段的映射。
**模糊查询 like 语句怎么写?**
使用 `#{}` 和 SQL 通配符 `LIKE`,例如:
```xml
SELECT * FROM table WHERE column LIKE CONCAT('%', #{value}, '%')
```
**通常一个 Xml 映射文件,都会写一个 Dao 接口与之对应,这个 Dao 接口的工作原理是什么?**
DAO 接口通过 MyBatis 的动态代理机制,MyBatis 在运行时会为接口生成代理类,调用接口方法时,会根据方法签名找到对应的 XML 映射文件中的 SQL 语句执行。
**MyBatis 是如何进行分页的?分页插件的原理是什么?**
MyBatis 通常使用分页插件(如 PageHelper)进行分页。分页插件拦截执行的 SQL 语句,在 SQL 语句末尾添加 `LIMIT` 子句,返回特定范围内的结果。
**MyBatis 是如何将 SQL 执行结果封装为目标对象并返回的?有哪些映射形式?**
MyBatis 使用 `resultMap` 和 `@Results` 注解将 SQL 结果映射到对象。有两种主要映射形式:
1. **自动映射**: MyBatis 自动匹配列名和属性名。
2. **手动映射**: 通过 `resultMap` 或 `@Results` 注解手动指定映射关系。
**如何执行批量插入?**
使用 MyBatis 的 `foreach` 元素:
```xml
<insert id="batchInsert">
INSERT INTO table (column1, column2) VALUES
<foreach collection="list" item="item" separator=",">
(#{item.column1}, #{item.column2})
</foreach>
</insert>
```
**如何获取自动生成的(主)键值?**
使用 `useGeneratedKeys` 和 `keyProperty` 属性:
```xml
<insert id="insert" useGeneratedKeys="true" keyProperty="id">
INSERT INTO table (column) VALUES (#{column})
</insert>
```
**在 mapper 中如何传递多个参数?**
使用 `@Param` 注解:
```java
@Mapper
public interface MyMapper {
@Select("SELECT * FROM table WHERE column1 = #{param1} AND column2 = #{param2}")
List<MyEntity> selectByParams(@Param("param1") String param1, @Param("param2") String param2);
}
```
**MyBatis 动态 SQL 有什么用?执行原理?有哪些动态 SQL?**
动态 SQL 用于根据条件生成不同的 SQL 语句。MyBatis 使用 `if`、`choose`、`trim`、`foreach` 等标签实现动态 SQL。执行原理是根据传入参数在运行时生成具体的 SQL 语句。
**XML 映射文件中,除了常见的 select、insert、update、delete 标签之外,还有哪些标签?**
还有 `<resultMap>`、`<sql>`、`<include>`、`<foreach>`、`<if>`、`<choose>` 等标签。
**为什么说 MyBatis 是半自动 ORM 映射工具?它与全自动的区别在哪里?**
MyBatis 需要手动编写 SQL 语句,是半自动 ORM。而全自动 ORM,如 Hibernate,会自动生成 SQL 语句,不需要手动编写。
**MyBatis 实现一对一有几种方式?具体怎么操作的?**
主要有两种方式:
1. **使用 resultMap**: 在 resultMap 中使用 `association` 元素。
2. **使用嵌套查询**: 在 select 语句中使用嵌套查询。
**MyBatis 实现一对多有几种方式?具体怎么操作的?**
主要有两种方式:
1. **使用 resultMap**: 在 resultMap 中使用 `collection` 元素。
2. **使用嵌套查询**: 在 select 语句中使用嵌套查询。
**MyBatis 是否支持延迟加载?如果支持,它的实现原理是什么?**
MyBatis 支持延迟加载。实现原理是通过代理对象在第一次访问延迟加载的属性时触发 SQL 查询。
**MyBatis 的一级、二级缓存:**
- **一级缓存**: 会话级别缓存,默认开启,范围是同一个 SqlSession。
- **二级缓存**: 映射级别缓存,需要配置,范围是同一个映射文件。
**什么是 MyBatis 的接口绑定?有哪些实现方式?**
接口绑定是指将 SQL 语句与接口方法绑定。实现方式包括注解方式和 XML 配置方式。
**使用 MyBatis 的 mapper 接口调用时有哪些要求?**
要求接口的方法名与 XML 配置文件中的 SQL 语句 ID 一致,并且方法参数和返回类型与 SQL 语句匹配。
**Mapper 编写有哪几种方式?**
1. **XML 映射文件**: 使用 XML 文件编写 SQL 语句。
2. **注解方式**: 在接口方法上使用注解编写 SQL 语句。
**简述 MyBatis 的插件运行原理,以及如何编写插件?**
MyBatis 插件通过拦截器机制拦截 SQL 执行过程中的某些点。编写插件需要实现 `Interceptor` 接口并在 MyBatis 配置文件中注册插件。