ibatis高级特性.docx

上传人:b****8 文档编号:23538565 上传时间:2023-05-18 格式:DOCX 页数:18 大小:425.21KB
下载 相关 举报
ibatis高级特性.docx_第1页
第1页 / 共18页
ibatis高级特性.docx_第2页
第2页 / 共18页
ibatis高级特性.docx_第3页
第3页 / 共18页
ibatis高级特性.docx_第4页
第4页 / 共18页
ibatis高级特性.docx_第5页
第5页 / 共18页
点击查看更多>>
下载资源
资源描述

ibatis高级特性.docx

《ibatis高级特性.docx》由会员分享,可在线阅读,更多相关《ibatis高级特性.docx(18页珍藏版)》请在冰豆网上搜索。

ibatis高级特性.docx

ibatis高级特性

iBATIS高级特性

1、主要内容

●关联对象

●事务

●延迟加载

●缓存

●动态标签

●读写CLOB和BLOB字段

●与spring的整合

2、关联对象

我们的大部分员工习惯了Hibernate的关联对象查询、级联删除、级联保存等特性,那么iBATIS是否提供同样的功能呢?

这是大部分人会关心的内容。

答案也许是另人失望的。

iBATIS可以关联查询,却没有提供级联保存和级联删除的特性。

下面我们介绍如何处理关联对象之间的查询、保存及删除问题。

2.1关联查询

iBatis为我们提供了两种方式关联查询,第一种N+1次查询,第二种新支持的查询方式。

两种方式需要根据具体的应用环境,作出合适的选择。

前一种由于多了一次和数据库的读取操作,所以读取速度慢了些,但是可以使用延迟加载减少内存的消耗。

而后一种方式多了些内存消耗,但是读取速度要快了。

定义一个需求:

我们在查询订单的同时希望查询出其关联的订单项。

2.2.1采用N+1次查询

首先看看我们的SQLMapped配置文件如何配置的:

我们可以看到,RESULT的select属性指向一个新的查询语句。

说明:

这个很好的解决了关联查询的问题,而且如果我们配置了全局的延迟加载,当真正用到订单项的时候,iBatis才为我们做查询的动作。

但是这却带来了另外一个问题,N+1次查询的问题。

也就是多了一次数据库的读操作,有一定的性能损失。

2.2.2新查询方式

首先看看我们的SQLMapped配置文件如何配置的:

我们可以看到,RESULT的resultMap属性指向一个resultMap标签定义。

说明:

与前面N+1次查询方式比较,由于只读取数据库一次,的确读取速度更快了,但是由于存在更多的内存消耗(N+1方式可以通过延迟加载来减少内存的消耗),所以我们该根据具体的应用情况而选择合适的方式。

2.2级联保存

在Hibernate中,我们可以使用级联保存,而iBATIS并没有提供该功能特性,此时我们需要自己保存关联的对象数据。

定义一个需求:

在保存订单的时候,希望一起保存其关联的订单项。

其DAO层可以定义如下两个方法分别保存订单和关联的订单项:

 

BMO层可以作如下调用:

这里涉及到的事务等后面讲解事务的时候再说明如何实现。

 

2.3级联删除

同样iBatis未提供级连删除的特性,我们要删除连关联表一起删除,也需要自己实现,其方式和保存类似,第一次删除关联的子表如订单项,再删除其主表如订单。

 

3、事务

3.1自动事务

所谓自己事务,就是说IbatisAPI单个方法自动划分为一个事务,不需要显示的开始、提交、结束。

3.2局部事务

其主要针对一种应用程序、一个资源、且一次只能处理一个事务。

如图:

其配置如下:

实现方式:

 

说明:

在Spring已经使用AOP申明式事务,所以像上面的配置文件及编码式事务使用到的可能性不大。

在蓝本工程的bss-BluePrint-spring-db.xml其Spring配置如下:

只要SMOImpl匹配的类,其insert*、update*、add*、del*将自动使用事务。

3.3全局事务

全局事务定义了一个更大的事务范围,它可以夸数据库、消息队列、甚至包含其它应用程序。

下图展示了一个全局的事务系统:

下图展示一个全局事务的配置方式:

接口和iBATIS的局部事务相同。

这样当需要从局部事务切换到全局事务的时候会很方方便,只要更改配置文件,不需要更改接口代码了。

4、延迟加载

配置方式如下图:

该属性默认值为true,若该属性值为true,当采用N+1次查询的时候,iBatis会在需要关联数据的时候才开始执行查询。

5、缓存

6、动态标签

主要分为五类动态标签:

6.1dynamic标签

Dynamic可以使用的属性如下:

属性

功能

Prepend(可选)

该值作为前缀添加到标签的结果内容提前。

但是当标签的结果内容体为空的时候,prpend值将不其作用。

Open(可选)

该值作为前缀添加到标签的结果内容提前。

如果结果内容体为空的时候,open值将不被附加到其前面。

Open值将在prepend属性值被添加到前缀之前先被添加前缀。

例如假设prepend=”when”,而open=”(”,则最终得到的组合是”when(“。

Close(可选)

该值作为后缀添加到标签的结果内容提后。

如果标签的结果内容体为空的时候,close值将不起作用。

使用示例如下:

 

6.2二元标签

二元标签的属性如下:

属性

功能

Property(必选)

参数对象用于同compareProperty或compareValye作比较的特性

Prepend(可选)

该值作为前缀添加到标签的结果内容提前。

但是当标签的结果内容体为空的时候,prpend值将不其作用。

Open(可选)

该值作为前缀添加到标签的结果内容提前。

如果结果内容体为空的时候,open值将不被附加到其前面。

Open值将在prepend属性值被添加到前缀之前先被添加前缀。

例如假设prepend=”when”,而open=”(”,则最终得到的组合是”when(“。

Close(可选)

该值作为后缀添加到标签的结果内容提后。

如果标签的结果内容体为空的时候,close值将不起作用。

romoveFirstPrepend(可选)

该值用于决定第一个嵌套的内容生成标签是否有移除其prepend值

compareProperty、compareValye(两个必有其一)

用来同property特性值作比较

二元动态标签如下:

Property属性与compareProperty或pareValye属性值作比较,看是否相同

Property属性与compareProperty或pareValye属性值作比较,看是否不同

Property属性是否大于pareProperty或pareValye属性值

Property属性与compareProperty或pareValye属性值作比较,看是否相同

Property属性与compareProperty或pareValye属性值作比较,看是否相同

Property属性与compareProperty或pareValye属性值作比较,看是否相同

使用示例如下:

6.3一元标签

一元标签的属性如下:

属性

功能

Property(必选)

参数对象用于同compareProperty或compareValye作比较的特性

Prepend(可选)

该值作为前缀添加到标签的结果内容提前。

但是当标签的结果内容体为空的时候,prpend值将不其作用。

Open(可选)

该值作为前缀添加到标签的结果内容提前。

如果结果内容体为空的时候,open值将不被附加到其前面。

Open值将在prepend属性值被添加到前缀之前先被添加前缀。

例如假设prepend=”when”,而open=”(”,则最终得到的组合是”when(“。

Close(可选)

该值作为后缀添加到标签的结果内容提后。

如果标签的结果内容体为空的时候,close值将不起作用。

romoveFirstPrepend(可选)

该值用于决定第一个嵌套的内容生成标签是否有移除其prepend值

一元标签如下:

确定参数对象中是否存在所指定的字段。

对于bean,它寻找一个特性;对象map,它寻找一个键。

确定参数对象中是否不存在所指定的字段。

对于bean,它寻找一个特性;对象map,它寻找一个键。

确定参数对象中是否为空。

对于bean,它寻找一个特性;对象map,它寻找一个键。

确定参数对象中是否不为空。

对于bean,它寻找一个特性;对象map,它寻找一个键。

确定参数对象中是否为空、空字符串、空集合或空的String.valueOf().

确定参数对象中是否为非空、非空字符串、非空集合或非空的String.valueOf().

使用示例如下:

6.4参数标签

参数标签的属性如下:

属性

功能

Prepend(可选)

该值作为前缀添加到标签的结果内容提前。

但是当标签的结果内容体为空的时候,prpend值将不其作用。

Open(可选)

该值作为前缀添加到标签的结果内容提前。

如果结果内容体为空的时候,open值将不被附加到其前面。

Open值将在prepend属性值被添加到前缀之前先被添加前缀。

例如假设prepend=”when”,而open=”(”,则最终得到的组合是”when(“。

Close(可选)

该值作为后缀添加到标签的结果内容提后。

如果标签的结果内容体为空的时候,close值将不起作用。

romoveFirstPrepend(可选)

该值用于决定第一个嵌套的内容生成标签是否有移除其prepend值

参数标签如下:

标签

说明

确定参数对象是否存在

确定参数对象是否不存在

使用示例如下:

6.5

iterate标签的属性如下:

属性

功能

Property(必选)

参数对象用于同compareProperty或compareValye作比较的特性

Prepend(可选)

该值作为前缀添加到标签的结果内容提前。

但是当标签的结果内容体为空的时候,prpend值将不其作用。

Open(可选)

该值作为前缀添加到标签的结果内容提前。

如果结果内容体为空的时候,open值将不被附加到其前面。

Open值将在prepend属性值被添加到前缀之前先被添加前缀。

例如假设prepend=”when”,而open=”(”,则最终得到的组合是”when(“。

Close(可选)

该值作为后缀添加到标签的结果内容提后。

如果标签的结果内容体为空的时候,close值将不起作用。

Conjunction(可选)

连接遍历集合(数组)时重复产生的那些SQL片段

romoveFirstPrepend(可选)

该值用于决定第一个嵌套的内容生成标签是否有移除其prepend值

使用示例如下:

7、读取CLOB和BLOB字段

在使用Oracle数据库时,读取CLOB和BLOB等大类型的数据一直是个比较犯难的事,一般都是通过JDBC代码来实现对CLOB和BLOB数据的读写,效果和性能都是最好的,但是代码也相当复杂,且代码难以重用。

7.1使用Spring的OracleLobHandler类处理

采用这种方法只对数据源是直接连接Oracle的JDBC驱动方式有效,如果你采用数据连接池作为数据源,则这种办法无效。

根据我们公司的BSS3.0的情况使用可能性不大。

所以这里不作介绍了。

7.2实现Ibatis的TypeHandlerCallback接口

sqlMap的配置如下:

说明:

通过实现ibatis的回调接口来实现,也有一定的局限性,需要新增一个类,配置也不方便,还可能会出错。

7.3通过配置ParameterMap和ResultMap来实现对LOB类型的读写

说明:

这样测试后发现也有其超过了4000个字符就不能插入,而CLOB类型的字段可以存4GB大小的字符。

这里只说了CLOB如何去实现,BLOB实现方式是一样的,只要注意其javaType既JAVA类型。

如下所示:

8、与Spring的整合

核心配置方法如下:

DAO实现方式:

说明:

只需要继承SqlMapClientDaoSupport,利用该类的提供

getSqlMapClientTemplate方法获取所需要的模板类,其接口方法和我们iBatis的SqlMapClient方法基本相同。

附件:

1、关于ibatis缓存

在你的xml配置文件中,每一个 cacheModel 元素,如下

  

      

      

      

                

(1)、 属性readOnly如果不写,默认是true,这时的缓存效果无疑最好,因为系统不需要考虑更新操作引起缓存与实际数据不一致的问题,只读缓存的例子是固化到数据库中的一些配置参数表。

但是,通常我们想缓存的数据是需要增删改的,这时务必记得要加上     readOnly = false;

(2)、属性serialize,如果不写,默认为false, 将它设为true,可以提高整体应用(而不仅仅是每个Session)的性能。

 这种缓存为每一个Session返回缓存对象不同的实例(复本)。

因此每一个Session都可以安全修改返回的对象.   注意,此时readOnly必须为false。

   如果你把它设为 true ,记得检查两件事,一件事是缓存中存放的对象(你想查询的POJO)必须是可序列化的, 即实现Serializable接口。

如果你有一个复杂对象属性,它也必须满足这个规则,你的整个对象树必须是可序列化的。

     另一件事是关闭sql-map-config中的延迟加载属性,即lazyload=false,原因是,它使用了动态代理机制, 那个代理对象并不是Serializable的。

   

   缓存类型的最佳适应情形:

 

   MEMORY    没有统一的对象重用模式的应用,或内存不足的应用。

   LRU       在较长的期间内,用户经常使用某些特定对象。

   FIFO      用户在短时间内持续引用特定的查询,而后很可能不再使用。

   

   根据个人实践,内存充足时使用LRU,否则使用MEMORY(WEAK)通常能获得较好的效果。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 小学教育 > 语文

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1