对象-关系映射基础
Hibernate中持久化类的访问者有两个:
1.Java应用程序
2.hibernate(何时调用get、set方法?)
Java应用程序不能访问持久化类的private方法,而hibernate没有这个限制,它可以访问各种级别的方法。
基本数据类型和包装类型
基本数据类型和包装类型对应的hibernate映射类型相同.
<property name=“price” type=“double” column=“PRICE” />
基本类型可直接运算、无法表达null、数字类型的默认值为0。
包装类默认值是null。当对于默认值有业务意义的时候需要使用包装类。
Hibernate访问持久化类属性的策略
1.property默认值:表明hibernate通过getXXX和setXXX来访问类属性。推荐使用。提高域模型透明性。
2.field:hibernate通过java反射机制直接访问类属性。对于没有javabean方法的属性可设置该访问策略。
<property name=“name” access=“field” />
除了设置property属性的access为field和property之外还可以自定义访问策略,需要创建实现net.sf.hibernate.property.PropertyAccessor接口的类.然后把类的完整名字
赋值给<property>元素的access属性
在持久化类的方法中加入程序逻辑
class Customer{ ….. private String firstname ; private String lastname ; public String getName(){ return firstname + “ ” + lastname ; } public void setName(String name){ StringTokenizer t = new StringTokenizer(name); firstname = t.nextToken(); lastname = t.nextToken(); } }
在customer.hbm.xml文件中无需映射firstname和lastname属性,而是映射name属性。
<property name =“name” column=“NAME” />
尽管类中并没有name属性,由于hibernate不是直接访问Name属性,而是调用get、set方法,因此建立了Firstname、Lastname和表之间的联系。
不管在类中是否存在name属性,只要在Customer.hbm.xml文件中映射了name属性,在hql语句中就能访问他。
Session.find(“from customer as c where c.name=‘tom’”)
在customer类的setOrders()方法中加入程序逻辑。
public void setOrders(Set orders){ this.orders = orders ; calprice(); } Public calprice(){ …… setAvgPrice(avgprice); }
在setSex()方法中加入数据验证逻辑
public void setSex(char sex){ if(sex != ‘M’ && sex != ‘F’){ throw new IllegalArgumentException(“Invalid sex”); } this.sex = sex; }
设置派生属性
利用<property>元素的formula属性,用来设置一个sql表达式,hibernate将根据它来计算出派生属性的值。
<property name=“totalprice” formula=“(select sum(o.PRICE) from ORDERS o where o.CUSTOMER_ID=ID)” /> <property name=“unitprice” formula=“BASE_PRICE*QUANTITY” />
另一种方案:在映射文件中不映射属性,在set方法中加入程序逻辑。
控制insert、update语句
映射属性 |
作用 |
<property> insert属性 |
若为false,在insert语句中不包含该字段,该字段永远不能被插入。默认值true。 |
<property> update属性 |
若为false,update语句不包含该字段,该字段永远不能被更新。默认值为true。 |
<class> mutable属性 |
若为false,等价于所有的<property>元素的update属性为false,整个实例不能被更新。默认为true。 |
<property> dynamic-insert属性 |
若为true,保存一个对象时,会生成动态insert语句,只有这个字段取值不为null才会把它包含到insert语句中。默认为false。 |
<property> dynamic-update属性 |
若为true,更新一个对象时,会生成动态update语句,只有这个字段取值不为null才会把它包含到update语句中。默认为false。 |
<class> dynamic-insert属性 |
若为true,等价于所有的<property>元素的dynamic-insert为true,保存一个对象时,动态生成insert语句,语句中仅包含取值不为null的字段。默认false。 |
<class> dynamic-update属性 |
若为true,等价于所有的<property>元素的dynamic-update为true,更新一个对象时,动态生成update语句,语句中仅包含取值不为null的字段。默认false。 |
<property name=“description” column=“`CUSTOMER DESCRIPTION`” />