每当我们开始一个新的J2EE(JavaEE)项目,我们都有一个决策需要确定,就是我们选取什么方式来进行与数据库的交互。现在比较流行的方式有这么几种:Hibernate,Spring JDBC Template(或者就是JDBC), ibatis。在这些工具的选择过程中,很多朋友都在讨论哪种工具可以使我们少写多少代码,或者是这个工具多么流行做为一个衡量尺度。个人认为这样的思考很合理,只是我个人经过一些实践,还有一个因素应该考虑,这就是你准备如何提高数据库访问的效率。
从前看过不少帖子讨论不同方式存取数据库的性能比较。在我看来,其实上述每种方式都有合适的改善数据库访问效率的途径,哪种工具的选择与我们更喜欢哪种方式来提高效率有很大关系。
这里我谈谈几种方式为提高存取效率考虑的不同之处。
在我们直接使用JDBC或者Spring JDBC Template这样的方式时,我们通常喜欢自己控制sql语句,写出效率最高的sql语句。在数据库的设计中,也处处充满了为了提高sql语句效率的设计。如我们为了减少sql语句的数量,我们有很多冗余字段,我们偏向于一次操作产生能够照顾尽可能多的记录条数。这样的方式也确实能够为我们生产最有效率的sql语句带来最大的自主性。
在使用Hibernate这样的对象映射工具时,由于设计上应该多从对象的角度来考虑问题,所以很多操作都是以一行记录(通常被实例化成一个对象)为主体进行的,所以直观看起来似乎效率就会低下。比如我们要批量更新一批数据,用这种方式,应该是有N个对象,每个对象都执行了Update操作,本来一条sql就可以搞定的事情用了N条sql。但是有趣的地方在于这些工具都会与另外的技术共存,那就是数据缓存。通过数据缓存,这N个对象的操作可能都是在缓存中完成,并不是我们想象的那么多次sql。类似的例子,本来我们要根据一批ID获取一批记录,如果直接用jdbc的方式,我们可以一条带in的sql语句完成,但是在对象为主的设计里,通常是每个对象都产生一次查询,在这里,解决效率问题的答案仍然是缓存。所以在这种方式下,怎样建立缓存,缓存的命中问题就成为了解决效率问题的关键。
ibatis这样的方式走了一些折中路线,它可以使我们方便的完成O/R映射,并且为了解决人们控制sql的愿望,可以自己指定进行数据操作的sql语句。但是由于它的这种不彻底,通常cache机制就没有Hibernate这么完备了。
我认为没必要争论哪种方式更有效率,因为我们可以看到,每种方式都有改善效率的途径。只是看我们工作的环境和我们开发的倾向性而已。完善的O/R映射架构更适合与醉心于面向对象思考问题的人,而原始的JDBC方式更适合于能够最大发挥sql效率并且对此产生乐趣的人