??xml version="1.0" encoding="utf-8" standalone="yes"?>中文字幕亚洲激情,亚洲av中文无码乱人伦在线观看,亚洲午夜国产精品无卡http://www.tkk7.com/Vikings/category/1404.htmlzh-cnFri, 02 Mar 2007 07:31:05 GMTFri, 02 Mar 2007 07:31:05 GMT60hibernate?Transaction 理http://www.tkk7.com/Vikings/articles/4818.htmlVikingsVikingsWed, 18 May 2005 16:07:00 GMThttp://www.tkk7.com/Vikings/articles/4818.htmlhttp://www.tkk7.com/Vikings/comments/4818.htmlhttp://www.tkk7.com/Vikings/articles/4818.html#Feedback0http://www.tkk7.com/Vikings/comments/commentRss/4818.htmlhttp://www.tkk7.com/Vikings/services/trackbacks/4818.htmlhibernate入门 - Transaction

Hibernate是对JDBC的轻量对象装QHibernate本n是不具备Transaction处理功能的,Hibernate的Transaction实际上是底层的JDBC Transaction的封装,或者是JTA Transaction的封装,下面我们详细的分析:

Hibernate可以配置为JDBCTransaction或者是JTATransactionQ这取决于你在hibernate.properties中的配置:

引用:
#hibernate.transaction.factory_class net.sf.hibernate.transaction.JTATransactionFactory
#hibernate.transaction.factory_class net.sf.hibernate.transaction.JDBCTransactionFactory


如果你什么都不配|,默认情况下用JDBCTransactionQ如果你配置为:

引用:
hibernate.transaction.factory_class net.sf.hibernate.transaction.JTATransactionFactory


用JTATransaction

不管你准备让Hibernate使用JDBCTransactionQ还是JTATransactionQ我的忠告就是什么都不配Q将让它保持默认状态,如下Q?

引用:
#hibernate.transaction.factory_class net.sf.hibernate.transaction.JTATransactionFactory
#hibernate.transaction.factory_class net.sf.hibernate.transaction.JDBCTransactionFactory


在下面的分析中我会给出原因?

一、JDBC Transaction

看看使用JDBC Transaction的时候我们的代码例子Q?

java代码: 

Session session = sf.openSession();
Transaction tx = session.beginTransactioin();
...
session.flush();
tx.commit();
session.close();



q是默认的情况,当你在代码中使用Hibernate的Transaction的时候实际上是JDBCTransaction。那么JDBCTransactionI竟是什么东西呢Q来看看源代码就清楚了:

Hibernate2.0.3源代码中的类
java代码: 

net.sf.hibernate.transaction.JDBCTransaction:

public void begin() throws HibernateException {
       
        log.debug("begin");       
        try {
                toggleAutoCommit = session.connection().getAutoCommit();
                if (toggleAutoCommit) session.connection().setAutoCommit(false);
        }
        catch (SQLException e) {
                log.error("Begin failed", e);
                throw new TransactionException("Begin failed with SQL exception: ", e);
        }       
        begun = true;
}


q是启动Transaction的方法,看到 connection().setAutoCommit(false) 了吗Q是不是很熟悉?

再来?

java代码: 

public void commit() throws HibernateException {       
        if (!begun) throw new TransactionException("Transaction not successfully started");       
        log.debug("commit");       
        try {
                if ( session.getFlushMode()!=FlushMode.NEVER ) session.flush();
                try {
                        session.connection().commit();
                        committed = true;
                }
                catch (SQLException e) {
                        log.error("Commit failed", e);
                        throw new TransactionException("Commit failed with SQL exception: ", e);
                }
        }
        finally {
                session.afterTransactionCompletion();
        }
        toggleAutoCommit();
}


q是提交ҎQ看到connection().commit() 了吗Q下面就不用我多说了Q这个类代码非常单易懂,通过阅读使我们明白Hibernate的Transaction都在q了些什么?我现在把用Hibernate写的例子译成JDBCQ大家就一目了然了Q?

java代码: 

Connection conn = ...;         <---   session = sf.openSession();

conn.setAutoCommit(false);     <---   tx = session.beginTransactioin();

...                            <---   ...

conn.commit();                 <---   tx.commit(); (对应左边的两?SPAN style="COLOR: #000000">)
conn.setAutoCommit(true);

conn.close();                  <---   session.close();


看明白了吧,Hibernate的JDBCTransactionҎ是conn.commit而已Q根本毫无神U可aQ只不过在Hibernate中,Session打开的时候,׃自动conn.setAutoCommit(false)Q不像一般的JDBCQ默认都是trueQ所以你最后不写commit也没有关p,׃Hibernate已经把AutoCommitl关掉了Q所以用Hibernate的时候,你在E序中不写Transaction的话Q数据库Ҏ没有反应?


二、JTATransaction

如果你在EJB中用HibernateQ或者准备用JTA来管理跨Session的长事务Q那么就需要用JTATransactionQ先看一个例子:

java代码: 

javax.transaction.UserTransaction tx = new InitialContext().lookup("javax.transaction.UserTransaction");

Session s1 = sf.openSession();
...
s1.flush();
s1.close();

...

Session s2 = sf.openSession();
...
s2.flush();
s2.close();

tx.commit();


q是标准的用JTA的代码片断,Transaction是跨Session的,它的生命周期比Session要长。如果你在EJB中用HibernateQ那么是最单不q的了,你什么Transaction代码l统都不要写了,直接在EJB的部|描q符上配|某某方法是否用事务就可以了?

现在我们来分析一下JTATransaction的源代码Q?net.sf.hibernate.transaction.JTATransaction:

java代码: 

public void begin(InitialContext context, ...
  ...
  ut = (UserTransaction) context.lookup(utName);
  ...


看清楚了吗? 和我上面写的代码 tx = new InitialContext().lookup("javax.transaction.UserTransaction"); 是不是完全一P

java代码: 

public void commit() ...
  ...
  if (newTransaction) ut.commit();
  ...


JTATransaction的控制稍微复杂,不过仍然可以很清楚的看出来Hibernate是如何封装JTA的Transaction代码的?

但是你现在是否看C什么问题? 仔细想一下,Hibernate Transaction是从Session中获得的Qtx = session.beginTransaction()Q最后要先提交txQ然后再session.closeQ这完全W合JDBC的Transaction的操作顺序,但是q个序是和JTA的Transactioin操作序d矛盾的!Q! JTA是先启动TransactionQ然后启动SessionQ关闭SessionQ最后提交TransactionQ因此当你用JTA的Transaction的时候,那么千万不要用Hibernate的TransactionQ而是应该像我上面的JTA的代码片断那样用才行?

ȝQ?

1、在JDBC上用Hibernate

必须写上Hibernate Transaction代码Q否则数据库没有反应。此时Hibernate的Transaction是Connection.commit而已

2、在JTA上用Hibernate

写JTA的Transaction代码Q不要写Hibernate的Transaction代码Q否则程序会报错

3、在EJB上用Hibernate

什么Transactioin代码都不要写Q在EJB的部|描q符里面配置


java代码: 


|---CMT(Container Managed Transaction)
|
|---BMT(Bean Managed Transaction)
        |
        |----JDBC Transaction
        |
        |----JTA Transaction




robbin:
你说“Hibernate的JDBCTransactionҎ是conn.commit而已Q根本毫无神U可aQ只不过在Hibernate中,Session打开的时候,׃自动conn.setAutoCommit(false)Q不像一般的JDBCQ默认都是trueQ所以你最后不写commit也没有关p,׃Hibernate已经把AutoCommitl关掉了Q所以用Hibernate的时候,你在E序中不写Transaction的话Q数据库Ҏ没有反应?
但sf.opengSession()Ӟq没有setAutoCommit(false)Q我想问的是Q如果不~写M事务代码Q如Q?
java代码: 

Session s = sf.openSession();
......
s.close();

数据库会不会有反应(此时应该是默认AutoCommit为trueQ?

另外Q我想问一下:
1. s.flush()是不是必ȝ
2. s.close()是不是一定要关闭
比如你上面提到的Q?
java代码: 

javax.transaction.UserTransaction tx = new InitialContext().lookup("javax.transaction.UserTransaction");

Session s1 = sf.openSession();
...
s1.flush();
s1.close();

...

Session s2 = sf.openSession();
...
s2.flush();
s2.close();

tx.commit();



s1不关闭,使用s2q行操作的代码中使用s1可不可以Q我觉得q样更加节约资源Q不需要反复的q接、关闭)



引用:
但sf.opengSession()Ӟq没有setAutoCommit(false)Q我想问的是Q如果不~写M事务代码Q如Q?
Session s = sf.openSession();
......
s.close();
数据库会不会有反应(此时应该是默认AutoCommit为trueQ?/TD>


不会有反应。在sf.openSession() 创徏Session实例的时候,已l调用了conn.setAutoCommit(false)了?


引用:
另外Q我想问一下:
1. s.flush()是不是必ȝ
2. s.close()是不是一定要关闭


s.flush不是必须的,s.close()会调用一ơs.flush()

s.close()正常情况下应该关闭,除非你是用ThreadLocal理Session?


引用:
s1不关闭,使用s2q行操作的代码中使用s1可不可以Q我觉得q样更加节约资源Q不需要反复的q接、关闭)


在这个例子中看不出来JTA的作用?
假设
java代码: 

Class{
  find() {
    Session s1 = sf.openSession();
    ...
    s1.flush();
    s1.close();
  }
}



java代码: 

Class{
  find() {
    Session s2 = sf.openSession();
    ...
    s2.flush();
    s2.close();
  }
}



java代码: 

Main {

  tx = ...;
  A.find();
  B.find();
  tx.commit();
}



看明白了吗?JTA的Transaction理是跨c调用的?BR>
zt:
http://forum.javaeye.com/viewtopic.php?t=264&postdays=0&postorder=asc&start=0


Vikings 2005-05-19 00:07 发表评论
]]>
JDO之前世今?/title><link>http://www.tkk7.com/Vikings/articles/4381.html</link><dc:creator>Vikings</dc:creator><author>Vikings</author><pubDate>Mon, 16 May 2005 13:41:00 GMT</pubDate><guid>http://www.tkk7.com/Vikings/articles/4381.html</guid><wfw:comment>http://www.tkk7.com/Vikings/comments/4381.html</wfw:comment><comments>http://www.tkk7.com/Vikings/articles/4381.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.tkk7.com/Vikings/comments/commentRss/4381.html</wfw:commentRss><trackback:ping>http://www.tkk7.com/Vikings/services/trackbacks/4381.html</trackback:ping><description><![CDATA[<TABLE cellSpacing=0 cellPadding=4 width="100%" border=0> <TBODY> <TR> <TD vAlign=top align=middle colSpan=2><FONT class=bigfont face=Tahoma><B>JDO之前世今?/B></FONT></TD></TR> <TR> <TD vAlign=top align=middle colSpan=2><span id="magbhkj" class=normalfont><FONT face=Tahoma><FONT color=#666666>2005-04-10</FONT>    sun2bin 原创    javaresearch.org    点击: 3</FONT></SPAN></TD></TR> <TR> <TD vAlign=top bgColor=#eeeeee colSpan=2 height=1><FONT face=Tahoma></FONT></TD></TR> <TR> <TD vAlign=top colSpan=2> <TABLE cellSpacing=1 cellPadding=4 width="100%" border=0> <TBODY> <TR> <TD vAlign=top> <div id="qegtojx" class=subhead><B>JDO之前世今?/B></DIV></TD></TR> <TR> <TD class=content vAlign=top> <TABLE width=200 align=right border=0> <TBODY> <TR> <TD></TD></TR></TBODY></TABLE>Q本文{自《CSDN开发高手?003W?0期)<BR><BR> <H3>1    Java与数据库应用QJDBC</H3><BR>Java发明以来Q在短短的几q之_q速占领了从桌面应用(J2SEQ到服务器(J2EEQ,再到型讑֤嵌入式系l(J2MEQ的应用开发市场,其语a吸取了SmallTalk的一切皆对象的理念,摆脱了C++的历史篏赘,z、自q风格赢得了很多开发者的喜爱。从JDK1.1开始,Java成ؓ实用的语aQ而不是被望的新品UQ再l过JDK1.2的大量增强(其是Collection FrameworkQ,JDK1.3的虚拟机效率提升QHotSpotQ,JDK1.4的融合百家之长(Logging、RegExp、NewIO{)Q现在已l是成熟E重Q颇昑֤安范?BR>在企业市场上,大部分的应用建立在数据库基础上,数据是企业的生命Q传l开发语aQ包括面向过E的C、面向对象的C++、变UPascal的DelphiQ非常棒的语aQ我用过四年Q,面向数据的PowerBuilder{等Q先后在数据库开发的舞台上展现风ѝJava当然不会放过q些Q于是,出现了JDBC。在JDBC的帮助下QJava也迅速渗入数据库开发的市场Q尤其是面向企业服务器的应用开发?BR>今天要谈的JDOQ与JDBC有非常密切的关系Q尽JDOq不是只面向JDBC的数据对象包装规范。下面先单地介绍一下JDBC?BR> <H4>1.1    关系数据库之癑֮争鸣QODBC</H4>关系数据库的历史一a隑ְQ我只能从我的接触经历和所见所闻,单地叙述一下。最早的时候,计算只在一些大型的研究机关露面Qƈ不是普罗大众可以涉及的。苹果电脑将个h电脑引入民间Q再随着IBM的PC标准开放,个h电脑逐步普及开来,加上微Y的DOS操作pȝQ以及Borland的Turbopd语言开发环境,老百姓发现原来电脑可以做q么多事Q后来,出现了DBASEQ一个简单的关系数据库系l,和SQL语言。后来,Borland看到了数据库的市场前景,推出了ParadoxQ也是当今Delphi和C++Builder中仍然用的ParadoxQ,一丑֍领了民用数据库的大部分江山,之后QBorlandq脆收购了DbaseQ后来又购买了InterBaseQ将数据库市场的领先优势一直保持到Windows3.0出现。这时候,微Y在Windows1.0?.0被h痛骂之后强地推?.0Q以及更E_?.1和Win32APIQ造就了个人电脑桌面操作系l的怸CQ在Borland未警觉的情况下,购买了同样具有类Dbase数据库技术的Fox公司Qƈq速将其易用化QŞ成了FoxBaseQ后来演变成FoxProQ逐渐过了BorlandQ成Z人电脑数据库的大戗微软再接再励,为简单易用而低负荷要求的数据库应用开发了AccessQ赢得了q大开发h员的心。当Ӟ同期的Oracle、Sybase、Informix{商用数据库凭专注于企业U数据库技术成为高端的几位领军人物。微软当然也x为高端数据库供应商之一Q于是自行开发一套面向企业应用的数据库Q不q很快项目夭折,微Y不甘心,购买了Sybase的底层TDS技术,包装成了SQL ServerQ凭微Y的高度易用性的特点Q也占领了不市场?BR>当市Z出现众多的数据库产品之后QBorland和微软都发现自己拥有的数据库产品挺多Q市Z不小Q不同的产品l用户带来不同的配置dQ不利于所有品的推广Q于是,两者纷U开始制定数据库讉K的规范,微Y推出了ODBCQ其面向开发h员的亲和性,逐步获得了认可,同时QBorlandU集了IBM和Novell也推ZIDAPI数据库接口规范,也就是今天BDE的核心,不过后来Novell和IBM先后退出,只剩Borland独力支撑。不qBorland是一个技术实力雄厚的公司Q其技术一向领先于微YQBDE的性能比初期的ODBC不知道要好多倍,后来微Y偷师学艺Q把q接池等技术加到ODBC中,在Delphi3.0及其BDE在市Z风光无限的时候,逐步赶了上来q有过。直C天,BDE仍是Borland的品线上的数据库访问标准,而微软如果不是将ODBC和多数数据库的客L内嵌qWindows的话Q估计BDE仍是市场的赢家。不q,微Y是玩弄市场的老手Q通过Ҏ作系l的垄断Q其数据库品和ODBC标准l究占据了多数开发市场?BR> <H4>1.2    从optional pack到JDK的标准API</H4><BR>Java开始涉及数据库应用后,Sun极力制定Java的数据库规范QJDBC API是cMODBC一PҎ据库讉K的底层协议进行最基本的包装,然后形成一套统一的数据访问接口,数据库连接、SQL语句句柄、结果集Q都带有ODBC的媄子。以方便配置为目的,Sun极力推荐完全瘦客L的TYPE 4型JDBC驱动Q这是一个不需要安装数据库客户端的驱动规范Q是现在使用最多的。当ӞZ保持与旧的数据库兼容QJDBC规范中包括了专用于连接ODBC的TYPE 1驱动和需要安装数据库客户端的TYPE 2驱动Q以及可以由厂商在数据库服务端专门提供面向JDBC的服务的TYPE 3驱动?BR>JDBC最早出现时Q还不属于标准JDK的一部分Q而是作ؓ一个额外包提供下蝲。后来,随着Java~写的数据库应用的的增多Q和JDBC规范本n的逐渐成熟QJDBCl于成ؓJDK1.1的一部分?BR>JDBC目前最新的?.0版本Q还有正在讨Z?.0版本。实际上Q在开发中使用得最多的q是1.0中的APIQ?.0中主要增加了可双向滚动的l果集、更新批处理{提高可用性和性能的APIQ?.0主要增加了连接池、可更新的结果集{特性?.0在可管理性、连接池规范化等斚w再做改进?BR> <H3>2    面向对象与数据库</H3><BR>现在的程序员Q没有不知道面向对象的。作为接q真实客观世界的开发概念,面向对象使程序代码更易读、设计更合理。在普遍存在的数据库应用领域Q开发h员对面向对象的追求从未停止过。从八十q代开始,有很多公司和研I机构在q行着面向对象与数据库l合的研I?BR> <H4>2.1    SmallTalk、C与C++、Delphi—Object Pascal、Java</H4>面向对象的语a最早有好几U雏形,IBM的SmallTalk是其中最为流行的Q在SmallTalk中,一切都是对象,一切都是类Q它面向对象的概念发挥C极致。面向对象的~程比v传统的面向过E的方式了一大步QZ认识刎ͼ原来软g可以q样写。不q,׃计算机基本结构与底层g体系和系lY件的限制QSmallTalkq不能在理想的性能前提下推q到普通的应用上,q一Ҏ旉制了SmallTalk的发展,接着QC语言的面向对象版C++出现了,׃使用C语言的h很多QC++很快成ؓ面向对象~程的主语a。不q,Z保证与C的兼容,C++保留了很多面向过E的痕迹Q比如恶心的指针、全局变量{等。Pascal的改q版Object Pascal相对来说安全许多Q后来Borlandq脆Object Pascal换了个名字,叫DelphiQ从此开创了一片面向对象编E的C界, Delphi的严谨语法和快速编译吸引了众多的应用开发者,加上Borland的完的VCLlg体系Q比起MFC来方便而容易,另外QDelphi完整的数据库lgQ也数据库开发变得简单而容易,Delphi再次成ؓ成熟的面向对象开发语a。微软当然不会放q这些,通过MFC内置到操作系l中Q微软的VC++也抢回一些市场。这也是Z么Delphi开发的应用E序~译后会比VC、VB开发的E序大的原因?BR>1995q_Sun的一个开发小l本来ؓ了小型嵌入式pȝ开发OAK语言Q结果无心插x成荫Q发展出了Java语言Q它是一个完全摆׃传统语言的各U负担的面向对象的语aQ当Ӟ也保留了一些非面向对象的核心(原始cdQ以保证速度。现在Java也ؓ最行的面向对象语a之一。当Ӟ微Y同样不会放过它,擅于模仿的微软立卛_Z个C#来与之竞争,q在C#中保留了一些变U的指针Q指代)以吸引传l的C开发者。关于这些语a的各自特点,q里׃一一赘述了?BR> <H4>2.2    数据库与数据对象?/H4><BR>数据库是企业U应用不可缺的Q因此,在面向对象流行的时候,数据库厂商也在进行着数据对象化的研究。这些研I在上个世纪八十q代初现端倪?BR>数据库的对象化一般有两个方向Q一个是在主的关系数据库的基础上加入对象化特征Q之提供面向对象的服务Q但讉K语言q是ZSQLQ另一个方向就是彻底抛弃关pL据库Q用全新的面向对象的概念来设计数据库Q这是对象数据库ODBMS?BR> <H5>2.2.1    关系数据库对象化、SQL99与JDBC3.0</H5>随着许多关系数据库厂商开始提供对象化服务Q各自的接口开始互不兼容,在经历一些麻烦之后,关系数据库厂商感觉到规范化的必要Q因为当初关pL据库雄霸天下时SQL92标准起了很大作用Q大家可以按照统一的编E方式来讉K高性能的商用数据库?BR>关系数据库厂商集中v来,重新对象化服务规范hQŞ成了SQL99规范Q将其中的对象结构等内容规范hQ开始一个崭新的面向对象的关pL据库QORDBMSQ的历程?BR>JDBC3.0是在这U情况下出台的,它将对关pL据库中的对象服务的访问API规范hQؓJavaq_提供了访问ORDBMS的标准方式。当ӞJDBC3.0对传l的SQL操作也进行了很多功能增强?BR>Oracle是一个传l的关系数据库厂商,在对象化的道路上QOracle当然采取q加对象化特征的道\Q以侵入数据对象化的市场Q保持Oracle在数据库领域的领导地位。如果说Oracle7.4使Oracle走向全盛的话Q从Oracle8开始,Oracle成为关pL据库加对象类型的先驱。在Oracle8中,我们可以定义一些数据结构(RecordQ,普通的cd包装在其中成为数据元素,然后可以在客L按Recordl构q行讉KQ初步提供了面向对象的数据库服务?BR> <H5>2.2.2    对象数据?/H5><BR>对象数据库就是采用全新的面向对象概念来设计数据库的全新数据库cd。在q方面,主要以一些大学研I机构进行设计和开发,有些也Ş成了产品Q不q由于市场方面的原因Q主要是关系数据库的Ҏ上手和市场绝寚w导地位)和ODBMS先天的一些弱点(比如查询引擎很难优化Q,使ODBMS没有象关pL据库那样行h?BR>不过对象数据库的对象化特点还是o人割舍不下,目前q是有一些很好的产品在市ZQ从商用的到免费的都用。目前在ODBMS领域占据领导C的是Versant、FastObjects和ObjectStore{几大厂商,q且Q市Z额也在逐步扩展。免费的产品包括C++~写的Ozone、纯Java的db4o{等。还有一些研I机构开发一些底层的面向对象数据库引擎,但只提供一些底层的APIQ不提供理斚w的功能,以及一些算法提供开攑ּ接口Q让厂商去选择和实现。比如美国威斯康新大学计机pL据库l的SHORE引擎Q就是一个非常出色的面向对象数据库引擎,现在q在U极的更CQ一些其它研I机构和数据库厂商采用它完成了自q特别的对象数据库Q比如专用于地理信息的数据库、专用于宇宙I间数据研究的数据库{等?BR>目前对象数据库最大的障碍是缺乏统一的规范,各个数据库厂商有各自的访问接口。对象数据库比v关系数据库来Q不只是基本的几U数据类型那么简单,它还涉及l承处理、多态等一大堆面向对象特征的实玎ͼ规范化道路当然困N重。这也是对象数据库无法普及的一个重要原因?BR>也有一些机构提Z一些徏议的规范Q比如制定Corba标准的OMG组的一个分lODMG提出的ODMG规范Q目前已l是3.0版本Q其中的OQL对象查询语言相当h吸引力。还有一些中立的机构提出了其它的一些标准化的对象访问APIQ也可算是面向对象数据库的规范之一。象前面提到的FastObjects和Ozone是W合ODMG3.0规范的?BR> <H3>3    Java对象映射</H3><BR>话说回来Q在一般的开发h员眼中,数据库就是指关系数据库,因此Q很多应用还是采用简单的JDBC来访问数据库。在开发的q程中,大家逐渐感觉到JDBC的局限性,比如调用复杂、容易生资源泄漏等{,与面向对象的Java语言有一D距,因此Q很多开发小l开始思考如何将应用中的数据q行对象化徏模,然后再想办法与JDBCl合hQ这是Java数据库开发中的层ZIL对象包装技术?BR> <H4>3.1    对象包装技?/H4><BR> <H5>3.1.1    传统包装与演?/H5><BR>传统包装֐思义Q就是最初出现的包装方式Q很多公叔Rl历q这一步,产生了很多风格各异的包装Ҏ。当ӞW者也有过q算丰富的尝试过E?BR>举例来说Q如果我们有一个用LQ?BR>public class User {<BR>    public int userId;<BR>    public String name;<BR>    public java.util.Date birthday;<BR>}<BR>我们可以其当作一个简单的数据c,然后写一些工h法来实现与JDBC的交互。这些方法,我们可以攑ֈ一个另外的工具cMQ也可以攑ֈUsercM作ؓ静态方法。这些方法包括简单的增、删、改、查Q以OracleZQ:<BR>public class User {<BR>    public int userId;<BR>    public String name;<BR>    public java.util.Date birthday;<BR><BR>    public static User addUser(String name, Date birthday) throws SQLException {<BR>        Connection conn = ? //获取一个JDBCq接<BR>        PreparedStatement ps = conn.prepareStatement(“…?; // 获取一个序列值来作ؓ用户标识<BR>        ResultSet rs = ps.executeQuery(); <BR>        rs.next();<BR>        User user = new User();<BR>        user.userId = rs.getInt(1); //d序列gؓ新用h?BR>        user.name = name;<BR>        user.birthday = birthday;<BR>        ps = conn.prepareStatement(“insert into ??; //插入用户数据记录的SQL<BR>        ps.setInt(1,user.id);<BR>        ps.setString(2,user.name);<BR>        ps.setDate(3,user.birthday);<BR>        ps.executeUpdate();<BR>        rs.close();<BR>        ps.close();<BR>        conn.close();<BR>        return user;<BR>}<BR><BR>public static void deleteUser(int userId) throws SQLException {<BR>    Connection conn = ?;<BR>    //?BR>}<BR><BR>public static User getById(int userId) throws SQLException {<BR>    //?BR>}<BR><BR>//?BR>}<BR><BR>以上是一个简单的数据包装的基本雏形,我们可以看到Q这是一个非常简单的JDBC包装Q一些代码可以模块化Q以实现重用。另外,q段代码q有很大隐患Q就是中途如果出现异常的话,׃使系l出现JDBC资源漏洞Q因为JDBC分配的资源(conn,ps,rs{)是不能被Java虚拟机的垃圾回收机制回收的。因此,我们的addUserҎ需要改成下面的样子Q?BR>    public static User addUser(String name, Date birthday) throws SQLException {<BR>        Connection conn = null;<BR>PreparedStatement ps = null;<BR>ResultSet rs = null;<BR>User user = new User();        <BR>try {<BR>conn = ? //获取一个JDBCq接<BR>ps = conn.prepareStatement(“…?; // 获取一个序列值来作ؓ用户标识<BR>        rs = ps.executeQuery(); <BR>        rs.next();<BR>        user.userId = rs.getInt(1); //d序列gؓ新用h?BR>        user.name = name;<BR>        user.birthday = birthday;<BR>        ps = conn.prepareStatement(“insert into ??; //插入用户数据记录的SQL<BR>        ps.setInt(1,user.id);<BR>        ps.setString(2,user.name);<BR>        ps.setDate(3,user.birthday);<BR>        ps.executeUpdate();<BR>    } finally { <BR>        //q里注意一定要按照创徏的顺序关闭JDBC资源Q?BR>    if(rs != null) try { rs.close(); } catch(SQLException ex) { ex.printStackTrace(); }<BR>            if(ps != null) try { ps.close(); } catch(SQLException ex) { ex.printStackTrace(); }<BR>        if(conn != null) try { conn.close(); } catch(SQLException ex) { ex.printStackTrace(); }<BR>    }<BR>        return user;<BR>}<BR><BR>所有的数据库访问方法都必须q行q样的包装,当我们的数据c达C定的数量后(比如十几个,几十个)Q这些方法占据了大量的代码,l护困难、出现BUGZ增多Qƈ且不易排错,其是资源漏z这U容易引h务器E_性问题的BUG?BR>Z保持数据cȝU洁Q我们可以将JDBC操作Ҏ集中C个公共工L中去完成Q这Pq个工具cM非常庞大Q但每个数据cM变得很简单,q种方式Q可以称作是DataAccessObject模式Q相当于EJB中的ValueObjectQ是q数据库细节的U对象模型?BR>q些都是最基本的存储处理,在基本增删改查(q里的查指按关键字查扑֯象)的基上,我们q需要进行复杂的匚w查询QSQLQ,q得我们的存储处理代码q一步复杂化。简单地Q我们可以写一个类似的ҎQ?BR>public static Collection findBy(String sql) throws SQLException {<BR>    //?nbsp;Q这里获取JDBCq接Q?BR>    Collection col = new Vector();<BR>    ps = conn.prepareStatement(sql);<BR>    rs = ps.executeQuery();<BR>    while(rs.next()) {<BR>        User user = new User();<BR>        user.userId = rs.getInt(1);<BR>        user.name = rs.getString(2);<BR>        user.birthday = rs.getDate(3);<BR>        col.add(user);<BR>    }<BR>    return col;<BR>    //?nbsp;Q同前,q里是清理JDBC资源的代码)<BR>}<BR>q就是一个查询接口的基本定义Q查询采用的语言仍是SQL?BR>如果我们需要将参数从SQL串中独立出来以节省数据库的解析时间ƈ规范化,我们q需要将查询条g作ؓ参数传递到q个Ҏ中去Q方法的接口改ؓQ?BR>public static Collection findBy(String sql, Object[] params) throws SQLException {<BR>    //?BR>    ps = conn.prepareStatement(sql);<BR>    for(int i = 0; i < params.length; i++) ps.setObject(i+1,params[i]);<BR>    //?BR>}<BR>调用的时候sql参数中会包含一些“?”号Q如Q?BR>select ID,NAME,BIRTHDAY from USER where ?nbsp;= ? and ?nbsp;> ? and ?BR>当然Q也有一些开发团队喜Ƣ将所有可能的查询都写L一个个的专用查询方法,在其中完成对应的SQL操作Q这一点类gEJBQLQ只不过是将EJBQL中容器实现的功能通过手工~码来实现。这样做使得查询受到限制Q但可以提供更保险的接口?BR>q有一些开发h员看到每个类中写q样一些查询方法得这个类的代码变得庞大,l护ȝQ便所有的查询Ҏ攑ֈ一个公q工具cM去,只是在方法中再加入一个参敎ͼClass cls来表C需要查询哪个对象,使得每个数据cd得紧凑一些。当Ӟq样的结果是那个公共cd得异常庞大,谁维护谁倒霉Q可以说是牺牲一人,q福团队。不q如果这个h心理素质不够好、压力承受能力不强的话,一些对数据cȝ改动可能会受C的阻,q时候就是“一夫当养I万夫莫开”?BR><BR>现在Q我们已l实C基本对象的包装,现在才能开始考虑更多的问题。首先,我们可能会从规范化的角度出发Q给每一个属性加上读写访问器getter/setterQ在前面的UsercMQ可能我们会基本属性部分写为:<BR>public class User {<BR>    private int userId;<BR>    private String name;<BR>    private Date birthday;<BR><BR>  //以下是针对以上属性的getter/setterQ一般可以用IDE工具生成    <BR>public int getUserId() { return userId; }<BR>    public void setUserId(int value) { userId = value; }<BR>    public String getName() { return name; }<BR>    public void setName(String value) { name = value; }<BR>    public Date getBirthday() { return birthday; }<BR>    public void setBirthday(Date value) { birthday = value};<BR><BR>    //?BR>}<BR><BR>q样Q一个比较规范的数据cd装就完成了?BR>另外Q我们知道,面向对象概念中,一个属性可以是另一个对象,也就是说Q对象之间是存在着引用关系的,q种关系q分Z对一、一对多、多对多{几U情c从一个既定对象出发,其某个属性可以是另一个对象,也可以是包含另一l对象的集合。那么,在我们的数据包装里面Q当然最好也能方便地处理对象之间的关pR假定现在我们又有一个数据类GroupQ?BR>public class Group {<BR>    public int grouId;<BR>    public String groupNameQ?BR>    public Set users; //set of User<BR>}<BR>q里Z单表明含义,暂不采用getter/setter?BR>而UserҎ属的Group有一个引用:<BR>public Group belongTo;<BR>在这里,User.belongTo和Group.users是一个一对多的关pR?BR>在我们的数据cMQ如何才能实现数据库的存取呢Q就是不考虑Group.usersq个反向关系Q光是User.belongTo是一件头疼的事。如果我们在取出一个User对象时同时将其Group对象也取出来Q可以保证不会在讉K某个用户的组时得C个null。不q这h几个~点Q?BR>1.    数据cȝ存取处理QJDBCQ变得复杂,需要执行很多SQLd才行Q有时候只需要访问User的基本属性时费旉和资源;其是对集合型属性的预读取,更加可?BR>2.    如果按这个逻辑Q双向的关系处理变得危险Q很Ҏ陷入d@环,如果要避免,必须在类代码中加入一些特别的机制Q也是很ȝ的事<BR>3.    如果对象之间的关pL更复杂的情况下,比如三个、四个对象之间互相关联,那就是一场噩梦,对代码的~写和维护都异常艰难<BR><BR>于是Q很多开发h员自然而然地退后一步,在UsercM只保留一个groupIdQƈ不保存Group对象Q这P可以User.belongTo属性变成intcdQ而另外写一个getterҎQ?BR>public Group getBelongTo() {<BR>    return Group.findById(belongTo);<BR>}<BR><BR>而在GroupcMQ干脆将users属性去掉,只保留一个方法:<BR>public Set getUsers() {<BR>    return new HashSet(User.findBy(“select ?nbsp;from USER where BELONG_TO=??new Object[]{ new Integer(groupId) }));<BR>}<BR>也许l心一点的读者已l看出来了,q里的几个方法都没有SQLException捕捉Q也没有在方法中声明Q也是说是有语法错误的Q因为SQLException不是一个RuntimeException。不错,实是这P不过我们q里Z单明了v见,省掉q些处理Q以更直接清楚地表达意思?BR><BR>q样Q实际上Q我们的对象关系包装已经名存实亡Q在cȝ内部有很多用于访问所引用对象的复杂代码,q些已经q背了我们将对象关系保持的初街有些开发h员甚至不在类中保留访问关pd象的ҎQ而是在客戯用时再去讉K另一对象cȝdҎQ如Q?BR>?BR>User user = User.getById(?;<BR>//对user对象q行一些访问,如显C其姓名{等<BR>Group group = Group.findById(user.belongTo);<BR>//对group对象q行一些访问,如显C组名等{?BR>?BR><BR>在这L代码里,实际上我们已l从Ҏ上退回了关系数据库的出发点,q与直接讉K数据表有多大区别呢?只不q是在表上面套了一层貌似面向对象的皮而已。不q的是,q种方式q存在于很多应用之中?BR><BR>从前面提到的q些面向对象包装的细节问题,我们可以看到q种传统包装方式的一些主要的~陷Q?BR> <LI>3.1.1.1    数据库命名与对象设计命名的一致性问?BR>很多时候,我们兴致勃勃地设计好一个类图,q且l过评审之后Q开始对它进行数据库包装Q这时候,发现有些属性名在具体的数据库中与该数据库的关键字冲H,不能用作表名或字D名Q必d数据表设计时采用另外的名Uͼ或者很ȝ地加上引h使用。于是,写数据库处理代码的h有意见了Q他必须很清楚地记得一个属性在cM是什么属性名Q在表中又是什么字D名Q在~写的类逐渐增多后,其是一个类l过历次变动之后Q或者经q很长时间又需要改动,q去处理q些JDBC代码Ӟ代码l护人员单要发疯了!<BR> <LI>3.1.1.2    对象的查询仍局限于SQLq一点也是这U简单的包装Ҏ最不能摆脱关系数据库的地方。上面也已经说过Q一些命名冲H带来了很多l护工作量,代码中必还保留数据表的命名体系Q而不是对象类的命名体pR这调用人员仍需要清楚记得两套命名体p,无论旉l过多久Q或者开发h员是否有动?BR>此外Q对于普遍需要用到的q表查询Q也l应用开发带来困难,q些地方仍不能突破SQL的限制?BR> <LI>3.1.1.3    SQL资源占用?BR>在处理对象集合访问或者处理集合类型属性时Q往往我们只能在同一个Connection中处理一切事务,q就要求一ơ性地集合中的对象全部读入,如果集合很大的话Q容易造成数据库拥塞,使得性能大打折扣Q适得其反。这斚w的优化也是很多开发h员一直在努力改进的?BR> <LI>3.1.1.4    对象关系处理复杂<BR>前面提过Q对象之间的关系处理上,普通的包装技术是一U表面上的处理,在访问时调用者仍需要用大量的代码进行处理,q且Q这q只是读取,在写入关pd性时会有更多的细节问题需要处理?BR> <LI>3.1.1.5    面向对象特色只能应用一部?BR>面向对象的包装到前面所说的为止Q都q只是很基本的处理,而面向对象的_֍Q承和多态,在这里得不到M帮助。我们放弃了很多合理的设计来q就数据库的包装?BR><BR>以上是基本数据包装的主要缺Pq有更多的小问题也需要额外的处理?BR>不过Q有责Q心的开发h员当然不会就此善|甘休,他们冥思苦惻I可能会用更好的方式来实现对象之间关系的处理,而且q会加入一些gq访问的机制Q将对象之间的引用在需要用的时候才去连接数据库取数据,另外Q在cȝl承上,他们也试囑֎在数据库包装上得C现?BR>值得感谢的是Q一些富有经验的团队在经历若q改q之后,毫不吝惜他们的成果贡献出来Qƈ其独立化,成ؓ可复用的lg。这也就是后来出现的对象包装产品Q包括商用的和免费的?BR> <H5>3.1.2    产品化包装中间g</H5><BR>面向对象的包装品化后,逐步推广开来,UC关系/对象映射QO/R Mapping。ƈ且,在品化的过E中Q品提供者在产品中逐渐提供了更多的功能。先是一些自动命名{换器得以应用Q将客户代码中的cd、属性名在内部处理的时候自动地转换到对应的数据库结构命名空间上Q这P应用开发的时候不再关心具体的数据库结构,不再需要记忆不同地命名体系Q只需要一心一意地Ҏcd来进行开发。在此之后,q些O/R Mapping产品的开发团队又向前q了一大步Q引入了词法分析器,提供面向对象的查询语aQ很多对象关pȝ查询使应用开发变得非常方便,使O/R Mapping产品上了一个新的台阶?BR> <LI>3.1.2.1    TopLink<BR>TopLink是一个非常早期的产品Q最初面向C++Q后来也实现了Java的映。TopLink性能优异Q功能强大,q且提供了独特的查询qo器机Ӟ以及对关pȝ处理和查询都非常有效Q于是,TopLink逐渐从商用化O/R Mapping产品中胜出,成ؓ市场上的最的映品。也正因一点,最大的关系数据库厂商Oracle其收购Q成为提供最强数据库和最强对象映中间g的厂商?BR> <LI>3.1.2.2    Castor、Hibernate<BR>TopLink虽然强大Q但太强大的东西免不了得意忘形,TopLink开始将用户锁死到自q产品上,查询方式是最H出的。它的查询体pd有很多别扭的概念Q在我看来是如此Q,但ؓ辑ֈ一般O/R产品不能辑ֈ的功能,开发者只能接受这些。慢慢地Q也产生U怨,再加上其高昂的h|让很多新老用h而却步。于是,免费的品开始崛赗?BR>免费的O/R Mapping工具有很多种Q这里只提其中最有媄响力的两U:Castor和Hibernate?BR>Castor是Exolabl织开发的面向Java的包装工P它最大的特色是实现了大部分的ODMG OQL规范Q在查询上,可以象完全用一个对象数据库一L图进行查询(后面会有介绍Q。它的原理是通过Java反射APId现属性的讄和读取。不q由于各U原因,Castor后来的版本更新越来越慢,最l停步在1.0之前Q成今未出到1.0正式版的O/R Mapping产品。不怎么P它还是一个相当不错的产品?BR>Hibernate是一个现在很火热的O/R Mapping产品Q目前已l出?.0版,它功能一样强大,同样使用Java反射APIq行对象的设|,但它的查询语a是一套比较独特的体系Q这一Ҏ点类似TopLinkQ但Hibernate更具有亲和力Q对关系的查询更方便Q只不过比vCastor来,在方便性和规范性上q是E逊一{V就目前状况而言QHibernate的用户量和技术支持要Z些?BR> <H4>3.2    面向对象的数据库查询</H4><BR>在对数据库进行面向对象研I的q程中,软g世界的开发h员和设计人员们发玎ͼҎ据库能够q行对象化的查询Q才是对数据库进行彻底的面向对象化。这体现在我们用一U全新的数据库查询语aQ能够很z易懂地Ҏ据库中的对象q行查询。一个典型的例子如下Q?BR>假设我们已经有前面提到的两个数据c:User和GroupQ它们之间有一对多的关p:User.belongTo和Group.users。在数据库中已经存在很多q两个类的实例,以及怺之间的关pR我们可以用下面的对象式查询语a来查询符合条件的User对象Q?BR>select * from User where User.belongTo.name=’GROUP1?BR>或?BR>select userId,name from User where User.belongTo.name=’GROUP2?BR>{等。从中我们可以看出,通过使用面向对象中的成员属性指定符?”,可以让我们达到SQL中的q表的效果,实际上,W一个句查询的SQL{h版本是:<BR>select a.* from USER a, GROUP b<BR>where a.BELONG_TO = b.GROUP_ID<BR>  and b.NAME = ‘GROUP1?BR><BR>由此可见Q对象式的查询语aQ比起实现同样功能的SQL语言来说Q简单了很多Q意义也更明,更符合用者的思维习惯。在cd比较复杂、查询涉及的cd比较多的时候,q种新型的查询语a体现出绝对的优势?BR> <H5>3.2.1    ODMGQOQLQJava Binding</H5><BR>在面向对象式查询语言的研I过E中Q开发h员们逐渐实现了相似的查询语言Q然后互惛_长补短,最l在ODMGl织Qwww.odmg.orgQ的l一下,形成了规范化的语aQODMG OQLQ这是一U完全面向对象的数据库查询语aQ语法与前面提到的类|不过考虑了更q泛的情况,语句更加z而严谨?BR>OQLq不是针ҎU语a的,它可以被应用到很多种开发语a中,它不象SQL那样只是U字W串式的查询语句Q因为面向对象查询中q必L供相关类的信息,所以OQL需要在~程语言中实C些特定的API?BR>目前QODMG的OQL已经被规范化地应用到SmallTalk、Java、C++q些面向对象的程序设计语a当中Q在ODMG的规范中Q这几个模块被称作SmallTalk Binding、Java Binding和C++ Binding?BR>不过Q由于历史原因,ODMGq没有象惌中地那样得到q泛应用Q现有的十几个面向对象数据库中,采用ODMG OQL规范的少之又,目前也只有FastObjeccts、Ozoneq些产品采纳了这个规范,而象Versantq样的大厂商q没有采取OQL来查询数据库Q而是自己定义了自q一套APIQ称作VQLQVersant Query LanaguageQ?BR>在JDO之前的O/R Mapping产品中,也有一些品用OQLQ有时候是其子集)Q比如Castor、Apache的Jakarta组开发的OJB{等?BR> <H5>3.2.2    W三方协?/H5><BR>软g世界是一个多姿多彩的世界QL那么一些好事之士不断地冒出新奇的想法。还有一些开发面向对象数据库的组l制定了自己的一套对象式数据库查询语aQ自q规范?BR>不过q些规范相对来说Q媄响力得多。比起ODMG来,可以说应用范围太,更不用说与SQLq样q泛应用的标准进行比较了?BR> <H5>3.2.3    EJBQL</H5><BR>SunZ使Java应用在企业数据库应用中Q不遗余力地推广J2EEQ在2001q的时候,推出了EJB2.0规范Q其中包含了富有特色的面向CMP方式的EntityBean的查询语aQEJBQLQ功能类gODMG OQLQ只不过只能在EJB发布旉态地存在于应用描q符中,不能在程序中动态地使用。这是EJBQL最大的qQ也许EJB3.0规范会将其动态化Q但C那一天,世界多半已经不是现在的样子了?BR> <H5>3.2.4    JDO</H5><BR>JDO中有最q规定的一个对象式查询语言规范Q称作JDOQLQ比起OQL来,JDOQL查询语a中的很多元素与Java语言紧密地结合在一P有的得麻烦,有些得规范,评论各不相同。从W者个人的角度来看Q这h利于没写q数据库应用、没用过SQL的新手很快地习惯JDOQLQ但实际上,有多h会在没写qSQLQ没了解q关pL据库的情况下ȝJDO写数据库应用呢?毕竟市场说明了一切。个为,JDO中对数据库对象的查询多少昑־有些累赘Q如果能更简化一点,那将更吸引用传lSQL的开发h员?BR> <H3>4    JDO历程与主要?/H3><BR>说vJDOQ其来由q有一D늉D的背景。Java语言在JDK1.1辑ֈ比较实用的目的后Q企业数据库应用也正是软g开发市Z的重要组成部分,Sun看到q一点后Q也希望通过Javaq个强大的武器在数据库开发市场攻占市Z额。JDK1.2推出后,Sun同时推出了面向企业应用的EJBQ对Zjava的中间g服务器框架进行了规范化定义,q就是J2EE。不q在JDK1.2ӞJava的速度q是不能与传l的C/C++和Delphiq样一些应用开发语a相比。ؓ了防止业界对Java的激情因此而消退QSun宣布在JDK中加入强大的虚拟机技术HotSpotQ其中包含更先进的垃圾收集算法和更优化的Java字节代码再编译技术(相当于JITQJavax~译技术)。HotSpot引v了Javax者的极大兴趣Q但Sun的HotSpot一拖再拖,最后包含在JDK1.3中出来时Q性能也没有象预期的那样好Q比起C++~译生成的代码来q是有一D距R?BR>q个时候,大家开始对Sun心存怀疑,而Sunqq一点,于是公众的注意力赶紧{UdEJB上,从EJB1.0到EJB1.1Q再到EJB2.0Q业界又开始关注J2EE中间件技术上来。很快,开发h同发现用EJB来编写数据库应用q是有很大的隑ֺQ虽然在分布式技术上EJB实有很大的价倹{在q个时候,Sun军_推出JDO技术作量的Java数据库访问规范,而这一点也受到很多传统O/R Mapping市场的欢q。ؓ了与传统O/R Mapping有所区别QSun一开始就高姿态地JDO定位成不只是面向关系数据库的Java规范Q而是针对所有的存储技术,包括面向对象数据库和其它cd的存储体p(如文ӞQ就象EJB EntityBean一P虽然。就W者的角度Q这个做法ɽW一版的JDO抛弃了很多传lO/R Mapping提供的面向关pL据库的功能,可以是一个失{?BR> <H4>4.1    规范提出、JSR</H4><BR>JDO最早是由Sun召集众多的O/R Mapping开发团队集中v来共同提出的Q首先是通过会议定了JDO需要包括的内容Q然后正式提Z个Java规范hQJSR-12Q,正式开始了JDO规范的制定。下面是主要的进展里E碑?BR>JSR #000012 approved in July 1999<BR>1999-8l徏的专家小l:包括Sun、Apple、BEA、IBM、Oracle、SAP、WebGain{?BR>2000-5 完成公开评论草案<BR>2000-6 在JavaOne上引?BR>2001-3 最l草?.93<BR>2001-5 最l草?.96公布<BR>2001-6 在JavaOne上启?BR>2001-11 最l草?.98<BR>2002-4 1.0版正式公?BR>2002-8 1.0.1修正?BR>2003-8 2.0规范启动<BR>?BR> <H4>4.2    Oracle与JDO</H4><BR>作ؓJDO专家l的重要成员Q同时作为最大的关系数据库厂商的OracleC昄非同一般。在JDO规范中,Oracle也可说是立下汗马功劳Q很多API的Ş成,Oracle都提供了很重要的参考意见,最l的投票Oracle也是毫不犹U?BR>可是Q世间的事L变化莫测的,在JDO1.0快出CӞOracle收购了TopLinkQ这一点Oracle的n份变得特D而复杂。TopLink是一个商业品,是以商业利益为目标的Q而Oracle也是q求利益最大化的典型商Ӟq一点与JDO的开攄背道而驰。因此,我们看到后期Oracle对JDO的不U极态度Q甚臛_前一늚JavaOne大会上有ZOracle的角度非正式地攻击JDO?BR> <H4>4.3    主要产品以及各自特点</H4><BR>在JDO规范制定的同Ӟ出现了几个主要的JDO产品Q有国的基于对象数据库的FastObjects j1、法国的支持Versant对象数据库、文件数据库、主RDBMS的LiDO、南非的JDOGenie、d国的JRelay{等Q这些都是很不错的JDO产品。下面列举一下我对主要的几个产品的印象:<BR>?nbsp;   LiDOQ法国LibeLis公司Q?BR>我对JDO的认识主要是通过LiDOq个产品Q它?002q?月的一份图文ƈ茂的教程中简要解说了JDO的用和优点。这个教E可以在q里下蝲Q?A ><FONT color=#0066cc>http://www.objectweb.org/conference/JDO.pdf</FONT></A>。LiDO的特色是大而全Q支持文件型数据库、RDBMS、ODBMSQ甚xXML数据库。不q配|较ȝ。最新版本是2.0RC?nbsp;<BR>?nbsp;   KodoJDOQ美国SolarMetrics公司Q?BR>Kodo是JDO的中砥׃一Q在JDO1.0q未最后通过的时候,它就是一个比较成熟的产品了,其特Ҏ注重性能和稳定性,目前最新版本是2.5.0Q是客户最多的产品?nbsp;<BR>?nbsp;   JDOGenieQ南非HemSphere公司Q?BR>q是目前我最推荐的品,最新版本是1.4.7Q性能也不错,E_性还有待验证Q但它有一个最大的特点Q集成性好Q最易学Q其公司的CTO David Tinker也是一个善解h意的q轻人,采纳了很多网友的意见对品进行改q,主要是在配置上非常方便,有一个专门的囑Ş界面工具Q可以进行配|、数据库生成、对象查询等{很实用的功能?BR>?nbsp;   JRelayQd国ObjectIndustries公司Q?BR>q也是一个出现得比较早的产品Q也有一个GUI工具用于配置Q曾几何Ӟq个工具q是相对很方便的Q但一q多q去了,好象没什么进展,最新版本是2.0Q我试过一D|_后来没有再跟进了?nbsp;<BR>?nbsp;   FrontierSuite for JDO Q美国ObjectFrontierQ?BR>q个产品与JRelay、Kodo一P可算是早期的JDO三个主要产品Q它支持正向开发和反向开发(Reverse EngineerQ。它的特色是反向工程Q从表结构生成数据类Q比较方便,与UML的结合也很强Q不q真正运行v来的时候,配置复杂?BR>?nbsp;   TJDOQ一跨国界的有志之士)<BR>q是一个在Sun提供的参考品(Reference ImplementationQ的基础上加入一些扩展功能而Ş成的一个免费品,目前最新版本是2.0beta3Q不q进展也~慢Q这个版本已l出现好几个月了没有q一步的更新?nbsp;<BR> <H3>5    目前状况与未来展?/H3><BR>?002q?月JDO1.0规范正式公布以来Q各个品层ZIP从商业到免费的层ơ,都有不错的品推出。象Kodo、Lido、JDOGenie{品都已经比较成熟Q可以考虑投入开发用。在2002q?月,JDO又推?.0.1修正版,修正?.0版规范中的一些文字错误,以及d地改q了部分异常定义Q不q改动都不大。从现在的情形来看,除了Kodo有一些大学的目用到外,好象q没看到多少使用JDO作开发的应用?BR>JDO毕竟是一个新技术,从概念上到实际应用上对其掌握的用戯不多Q而这些品在配置、用上的方便性易用性还有待大幅度改q,因此Q真正用JDO来开发项目的用户q廖廖无几,臛_我还不知道有哪些目使用了JDO。我自己也尝试用JDO来开发项目,但由于一些JDO1.0版本中还不够完善的一些硬伤(比如不支持关pL据库l计功能Q,使我对JDO仍处于观望阶Dc?BR>在八月中旬进行的JDO2.0规划会议中,来自各国的各个JDO产品厂商、JDO技术咨询公司、JDO研究机构的代表汇聚一堂,各自收集到的用户对JDO2.0的需求ȝhQ提Z个个的新的议题,q且定了每个议题的JDO规范撰写负责人,比如高fetchGroupҎ由目前实现得最好的JDOGenie的CTO David Tinker负责Q关于managed-relationshipҎ由Kodo的品ȝ负责Q用戯求最多的JDO对象与PersistenceManager的脱?重挂钩特性由Sun的Craig Russell亲自操刀Q等{?BR>最h吸引力的JDO2.0议题Q笔者个为是专门为关pL据库讄的子规范JDO/RQ这也是我一直以来最兛_的,q将使目前JDBC的开发将可以被JDO完全取代Qƈ且保证开发过E保持面向对象的特色。还有一些将一个类映射到多个表之类的特性也在规范化的列表上Q这有利于DBA在不影响应用开发的前提下根据需要更Ҏ据表l构Q实现更好的性能。类似的新特性还有很多,_略地看Q这些都规范化v来后Q真不知道各个厂商还能做什么样的扩展特性,也许以后厂商之间拼的只能是技术支持服务和产品性能了,当然Q最后还有h格的竞争?BR>说了q么多,我想大家兛_的还是JDO2.0到底什么时候能出来Q我们什么时候可以用上它Q什么时候有中文版品,h到底如何。这些问题目前笔者还无法一一回答Q只能根据笔者所掌握的信息初步解释一下。据前几天的JDO2.0启动大会上David Jordan的预期,JDO2.0正式版将?8个月后正式完成。那正式完成后厂商什么时候才能提供符合规范的产品呢?q个问题不用担心Q因范在制定的过E中会不断地公布公众预览版(Public ReviewQ,q样Q厂商可以先实现其中的功能,{规范正式完成后Q也不会有太大的变化Q厂商也不会需要太多时间来跟进最l规范。所以,我估计一q之后,我们可以在JDO2.0上进行开发了。至于h格如何,1.0规范的品初步印象是每个开发h员需要一个LicenseQ一个License大概2000元。如果JDO2.0产品的hD保持q么늚话(臛_对中国用h_Q我们也q有很多免费Q如JPOXQTJDOQ或半免费(如JCredoQ品可以选择。最后一个关于中文版的问题,有待于厂商对中国市场的考察Q或者看看是否有国内的JDO产品了。不q,在JDO2.0规范制定的同Ӟ我们可以先集众h之力其普及Qq大的用Java语言q行数据库开发的开发h员都来认识JDOQ了解JDOQ甚臛_其用到项目开发之中?BR>也许QJDO的目标已l吸引了Java世界以外的hQ微软发Cq一点,也立卌划在.NET体系中加入一个仿照JDO的中间gQ具体是采用ObjectStore的品,ObjectStore是一个同时做JDO?NET-DOQ姑且用这个名Uͼ的公司?BR><BR>在这里,W者可以大胆地预测Q在未来的一两年内,JDO在Java世界大放光彩Q?BR> <H4>5.1    一点花i?/H4><BR>?003q?月D行的JavaOne大会上,JDO备受瞩目Q很多开发者或开发组l对其生了极大的兴,在各大网站媒体上也频频曝光,大多对其评h不错Q当Ӟ也有一些负面的评h?BR>不过Q网站上的报道也不可信Q比如服务器领域的权威网站TheServerSide.com上介lJavaOne大会W二天关于JDO的一ơ会议的报道有误导之嫌Q从报道的内Ҏ看,好象会议用来{疑与交的的最后五分钟全被一个好事者占据,q个人拼命鼓吹Oracle的TopLink解决Ҏ和一些易用性的改进Q从而攻击JDO的市场前景。后来,我就q一信息与参加会议的JDO专家l的David Jordan交流Ӟ他纠正了我的错误理解Q实际情形是Q那个好事者是一个积极的JDO拥护者,他花了超q五分钟旉向大家揭露Oracle的TopLink改进实际上也是抄袭JDO的概念而进行的一些API改动Q不q有一Ҏ相同的,q个好事者占据了大家的提问时_使这ơ会议在意犹未尽中结束?BR><BR>    本文的版权属于笔者本人,但欢q{载,前提是注明出处和原作者。另外,Ƣ迎?A class=l2 target=_blank><FONT color=#0066cc>我的专栏</FONT></A>中查看我的另几篇文章Qƈ提出宝贵意见Q?BR></LI></TD></TR></TBODY></TABLE></TD></TR></TBODY></TABLE><img src ="http://www.tkk7.com/Vikings/aggbug/4381.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.tkk7.com/Vikings/" target="_blank">Vikings</a> 2005-05-16 21:41 <a href="http://www.tkk7.com/Vikings/articles/4381.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss> <footer> <div class="friendship-link"> <p>лǵվܻԴȤ</p> <a href="http://www.tkk7.com/" title="亚洲av成人片在线观看">亚洲av成人片在线观看</a> <div class="friend-links"> </div> </div> </footer> վ֩ģ壺 <a href="http://zz198.com" target="_blank">þþƷAVDz18</a>| <a href="http://www678678.com" target="_blank">ִִӲˬƵ</a>| <a href="http://773311h.com" target="_blank">97Ƶѹۿ2</a>| <a href="http://gzmandala.com" target="_blank">йavƬ</a>| <a href="http://taobaohuopin.com" target="_blank">һëƬȫ</a>| <a href="http://s4lm0x.com" target="_blank">žžþùƷ6</a>| <a href="http://czdlglass.com" target="_blank">ѾƷþþþþĻ </a>| <a href="http://sanyoumiaomu.com" target="_blank">ѹۿƵ</a>| <a href="http://www-15706.com" target="_blank">պƵ߹ۿ</a>| <a href="http://www1688mz.com" target="_blank">ձһ</a>| <a href="http://www026qqcom.com" target="_blank">ձƵ</a>| <a href="http://woaisouluo.com" target="_blank">avƬѿ</a>| <a href="http://ocn888.com" target="_blank">jjzz߲Ź</a>| <a href="http://bbby6.com" target="_blank">պ߾Ʒһ</a>| <a href="http://micehunan.com" target="_blank">˾Ʒձר61</a>| <a href="http://zz1220.com" target="_blank">߾ƷһӰȷ</a>| <a href="http://kingco-glaze.com" target="_blank">߲޵һĻ</a>| <a href="http://d8139.com" target="_blank">Ƶ߹ۿ</a>| <a href="http://bxd888.com" target="_blank">˾þþƷ</a>| <a href="http://slotvip24.com" target="_blank">޾ƷŮþþþþþ</a>| <a href="http://chaikexin.com" target="_blank">޹</a>| <a href="http://yeyaweiban.com" target="_blank">hƵѸ߹ۿ</a>| <a href="http://6wss.com" target="_blank">һ</a>| <a href="http://0515bh.com" target="_blank">պѲ</a>| <a href="http://dnf1000.com" target="_blank">ŷƵ</a>| <a href="http://519vip.com" target="_blank">ѹۿһëƬ</a>| <a href="http://yes5555.com" target="_blank">߹ۿ</a>| <a href="http://jipiao020.com" target="_blank">޳AVƬ</a>| <a href="http://zgdhuibao.com" target="_blank">һ</a>| <a href="http://ur5r2kr.com" target="_blank">޾Һ</a>| <a href="http://wwwy6x22.com" target="_blank">۵Ƶѹۿ</a>| <a href="http://yx6768.com" target="_blank">þþþþྫƷֱ</a>| <a href="http://liexion.com" target="_blank">һëƬ߲Ƶ</a>| <a href="http://www-36664.com" target="_blank">Ʒþ</a>| <a href="http://yeyaweiban.com" target="_blank">ѿٸƵ</a>| <a href="http://snsdtv.com" target="_blank">þù޾ƷӰԺ </a>| <a href="http://33uub.com" target="_blank">޸Ļַ</a>| <a href="http://58rjz.com" target="_blank">޹Ʒva߲</a>| <a href="http://600c20.com" target="_blank">ͼƬӰ</a>| <a href="http://skcncar.com" target="_blank">߹ۿ</a>| <a href="http://adcadm.com" target="_blank">þþƷѹۿ</a>| <script> (function(){ var bp = document.createElement('script'); var curProtocol = window.location.protocol.split(':')[0]; if (curProtocol === 'https') { bp.src = 'https://zz.bdstatic.com/linksubmit/push.js'; } else { bp.src = 'http://push.zhanzhang.baidu.com/push.js'; } var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(bp, s); })(); </script> </body>