10月份带领小伙伴们巩固Java编程知识,掌握精髓编程思想和开发技巧,为接下来学习网络编程和Spring等奠定基础。本课程难度在中等以上,要求学生已经熟悉简单的Java编程语法。每晚包括两个课时。课后会安排练习作业。大家有问题请到QQ学习群(915851077)交流作业,老师课后也会在QQ群里给大家答疑。直播课时安排:www.javathinker.net/zhibo.jsp
后端Web开发我写了两本书《Tomcat与Java Web开发技术详解》和《精通Spring: Web技术开发详解》,其中《精通Spring》还在由清华大学出版社编辑排版中。写完了,不过瘾,应该再写一本介绍前端开发的书,这样才能给读者呈现如今流行的Web开发的整体架构,于是去年10月开始动工写Vue.js,用的是目前最新的Vue3版本,到今年6月中旬交稿,估计半年后可以和读者们见面哦。内容简介本书
孙卫琴的《精通JPA与Hibernate》的源代码下载
这些年耕耘于Java技术书籍的创作,写了十来本书。许多热心读者喜欢和我交流所创作书的知识以及相关技术。为了便于大家互相探讨,互相学习,就设立了一个QQ学习群。如果您有疑问,欢迎到此群交流。
后端Web开发写了两本书《Tomcat与Java Web开发技术详解》和《精通Spring: Web技术开发详解》,其中《精通Spring》还在由清华大学出版社编辑排版中。 写完了,不过瘾,应该再写一本介绍前端开发的书,这样才能给读者呈现如今流行的Web开发的整体架构, 于是去年10月开始动工写Vue.js,用的是目前最新的Vue3版本,到今年6月中旬交稿,估计半年后可以和读者们见面哦。 这本书交
EntityManager的detach()方法用于从第一级缓存中清除一个特定的对象。对于第二级缓存,JPA API提供了javax.persistence.Cache接口,它具有控制第二级缓存的evict()方法,能从第二级缓存的实体数据缓存中删除特定的数据。javax.persistence.Cache接口只能控制实体数据缓存。如果要控制其他类型的缓存,需要使用Hibernate API提供的org.hibernate.Cache接口。以下controlCache()方法演示了JPA API以及Hi
乐观锁是由应用程序提供的一种机制,这种机制既能保证多个事务并发访问数据,又能防止第二类丢失更新问题。在应用程序中,可以利用Hibernate提供的版本控制功能来实现乐观锁。既可以用一个递增的整数来表示版本号,也可以用时间戳来表示版本号,跟踪数据库表中记录的版本。下面介绍利用整数类型的版本控制属性对ACCOUNTS表中记录进行版本控制的步骤。(1)在Account类中定义一个代表版本信息的version属性,这个属性用@Version注解来标识:@Version@Column(name="VERSIO
Java应用通过JTA API声明JTA事务的步骤如下。 (1)在Hibernate配置文件中配置数据源以及JTA平台属性: hibernate.connection.datasource= java:comp/env/jdbc/SAMPLEDB hibernate.transaction.coordinator_class=jta hibernate.transaction.jta.platform=JBossTS (2)在程序中创建javax.naming.InitialContext对象: Con
在受管理环境中,如JBoss应用服务器,由容器负责构造数据源,即javax.sql.DataSource的实例,然后把它发布为JNDI资源,Hibernate的DataSourceConnectionProviderImpl类充当这个数据源的代理,这个类位于org.hibernate.engine.jdbc.connections.internal包中。 有些Servlet容器,如Tomcat,也能负责构造数据源,并能把它发布为JNDI资源,因此Hibernate也能从Tomcat容器中获得数据源。 以To
1. 立即左外连接 以下程序覆盖映射代码中指定的检索策略,显式指定对与Customer关联的Order对象采用立即左外连接检索策略: //JPQL检索方式 List<Customer> result=entityManager .createQuery("from Customer c left join fetch c.orders o " +"where c.name like 'T%' ",Customer.class) .getResultList(); //QBC检索方式
JPQL查询语句中的group by 子句用于分组查询,它和SQL中的用法很相似。下面举例说明它的用法。 (1)按照姓名分组,统计CUSTOMERS表中具有相同姓名的记录的数目: //JPQL检索方式 Iterator<Object[]> it=entityManager .createQuery("select c.name,count(c) from Customer c group by c.name", Object[].class) .get
1. JPQL的参数绑定 1.1 按参数名字绑定 在JPQL查询语句中定义命名参数,命名参数以“:”开头,形式如下: TypedQuery<Customer> query=entityManager.createQuery( "from Customer as c where c.name=:customerName " +"and c.age=:customerAge",Customer.class); 以上JPQL查询语句定义了两个命名参数“customerName
当批量查询数据时(例如查询CUSTOMERS表中所有记录),如果数据量很大,会导致无法在用户终端的单个页面上显示所有的查询结果,此时需要对查询结果分页。假如CUSTOMER表中有99条记录,可以在用户终端上分10页来显示结果,每一页最多只显示10个Customer对象,用户既可以导航到下一页,也可以导航到前一页。 Query接口提供了用于分页获取查询结果的方法: setFirstResult(int firstResult):设定从哪一个对象开始检索,参数firstResult表示这个对象在查询结果中的索
采用JPQL检索方式时,在应用程序中需要定义基于字符串形式的JPQL查询语句。QBC API提供了检索对象的另一种方式,它提供了一种更加面向对象的查询方法,应用程序不需要提供查询语句,而是通过QBC API中的相关的接口和类来设定需要检索的数据,包括设定检索条件等。 QBC API位于javax.persistence.criteria包中,主要包括以下接口: CriteriaBuilder接口:它是生成CriteriaQuery实例的工厂类。 CriteriaQuery接口:它是主要的查询接口,通过它来
JPQL(JPA Query Language)是面向对象的查询语言,它和SQL查询语言有些相似。在JPA提供的各种检索方式中,JPQL是使用最广的一种检索方式。它具有以下功能: 在查询语句中设定各种查询条件。 支持投影查询,即仅检索出对象的部分属性。 支持分页查询。 支持连接查询。 支持分组查询,允许使用having和group by关键字。 支持调用各种函数。 支持子查询,即嵌入式查询。 支持动态绑定参数。 以下程序代码用于检索姓名为“Tom”,并且年龄为21的Customer对象: //创建一个Q
建立域模型和关系数据模型有着不同的出发点: 域模型是由程序代码组成的,通过细化持久化类的粒度可提高代码可重用性,简化编程。 关系数据模型是由关系数据组成的。在存在数据冗余的情况下,需要把粗粒度的表拆分成具有外键参照关系的几个细粒度的表,从而节省存储空间;另一方面,在没有数据冗余的前提下,应该尽可能减少表的数目,简化表之间的参照关系,以便提高访问数据库的速度。因此,在建立关系数据模型时,需要在节省数据存储空间和节省数据操纵时间这两者之间进行折中。 由于建立域模型和关系数据模型的原则不一样,使得持久化类的数
如果Address类没有OID,那它就是组件类。由于Address类没有OID,因此不能通过EntityManager或Session来单独保存、更新、删除或加载一个Address对象。例如,以下每行代码都会抛出IllegalArgumentException异常: entityManager.find(Address.class,Long.valueOf(1)); entityManager.persist(address); entityManager.remove(address); 以上代码运
在持久化类中通过注解设定的检索策略是固定的,要么为延迟检索,要么为立即检索。但应用逻辑是多种多样的,有些情况下需要延迟检索,而有些情况下需要立即检索。 Hibernate允许在应用程序中覆盖持久化类中设定的检索策略,由应用程序在运行时决定检索对象图的深度。 以下代码两次调用Query的getResultList()方法,都用于检索OID为1的Customer对象: //第一个Query.getResultList()方法 entityManager .createQuery("from Cust
以下SQL代码定义了一个名为findCustomers的存储过程,p_age为输入参数,p_count为输出参数: delimiter // create procedure findCustomers(in p_age integer,out p_count integer) begin select count(*) into p_count from CUSTOMERS where AGE>p_age; select name from CUSTOMERS; end // JPA API中
对于一对多关联和多对多关联,应该优先考虑使用默认的延迟检索策略。在Customer类中,以下代码对orders集合属性采用延迟检索策略: //采用默认的延迟检索策略 @OneToMany(mappedBy="customer") private Set<Order> orders = new HashSet<Order>(); 或者: //显式设置延迟检索策略 @OneToMany(mappedBy="customer", fetch=FetchType.
假定建立了从Category(商品类别)类和Item(商品)类的双向多对多关联。在Category类中需要定义集合类型的items属性,并且在Item类也需要定义集合类型的categories属性。下图显示了Category类和Item类的关联关系。 下图显示了CATEGORIES表、ITEMS表和CATEGORY_ITEM表的结构。 在Category类中,映射items属性的代码如下所示: @ManyToMany(cascade=CascadeType.PERSIST) @JoinTable( .
Bag集合中的对象不按特定方式排序,但是允许有重复对象。在Java集合API中并没有提供Bag接口,Hibernate允许在持久化类中用List来模拟Bag的行为。假定Customer对象的images集合中允许存放重复的照片文件名,可以把images属性定义为List类型: private List<String> images=new ArrayList<String>(); 在数据库中定义了一张IMAGES表,它的CUSTOMER_ID字段为参照CUSTOMERS表的外键,由
1. 设置Spring的配置文件 在Spring的配置文件applicationContext.xml中,配置C3P0数据源、EntityManagerFactory、JpaTransactionManager等Bean组件。applicationContext.xml文件位于范例程序的classpath根路径下,以下是它的源程序。 /* applicationContext.xml */ <?xml version="1.0" encoding="UTF-8"?> <beans xml
假定Customer对象的images集合中不允许存放重复的照片文件名,因此可以把images属性定义为Set类型: private Set<String> images=new HashSet<String>(); 在数据库中定义了一张IMAGES表,它的CUSTOMER_ID字段为参照CUSTOMERS表的外键,由于Customer对象不允许有重复的照片文件名,因此应该把IMAGES表的CUSTOMER_ID和FILENAME字段作为联合主键。 以下是IMAGES表的DDL定
表的结构如下: 在域模型中,Company类和Employee类之间为一对多的双向关联关系(假定不允许雇员同时在多个公司兼职),Employee类为抽象类,因此它不能被实例化,它有两个具体的子类:HourlyEmployee类和SalariedEmployee类。由于Java只允许一个类最多有一个直接的父类,因此Employee类、HourlyEmployee类和SalariedEmployee类构成了一棵继承关系树。 1.映射Company类 Company类与Employee类是一对多的关联关系,C
本文选自《精通JPA与Hibernate:Java对象持久化技术详解》,清华大学出版社出版,作者孙卫琴。1.设置Spring的配置文件在Spring的配置文件applicationContext.xml中,配置C3P0数据源、EntityManagerFactory、JpaTransactionManager等Bean组件。applicationContext.xml文件位于范例程序的classp
本文对JPA的EntityManager接口与Hibernate的Session接口进行了比较,本文参考《精通JPA与Hibernate:Java对象持久化技术详解》,作者:孙卫琴。EntityManager接口与Session接口的许多功能很相似,以下表对这两个接口的方法做了对比。从以上表可以看出,EntityManager接口中的大部分方法在Sesson接口中都有对应的方法。EntityManager的remove()方法与Session的delete()方法的作用基本上相同,两者的一个小小区别是
JPA API 的EntityManager 以及Hibernate API的Session都有一个merge()方法,它们的作用相同,能够把一个游离对象的属性复制到一个持久化对象中。当Session用update()方法关联一个游离对象时,如果在持久化缓存中已经存在一个同类型的并且OID相同的持久化对象,那么update()方法会抛出NonUniqueObjectException:customer1.setName("Jack");//假定customer1为游离对象,OID为1Session
行异步操作,例如。
Copyright © 2005-2023 51CTO.COM 版权所有 京ICP证060544号