(转)兑现CompositeUserType接口
(转)实现CompositeUserType接口
Hibernate还提供了一个CompositeUserType借口,它不仅能完成和UserType相同的功能,而且还提供了对Hibernate查询语言(HQL)的支持.下面通过例子来介绍CompositeUserType接口的方法.
假定在Customer类中包含了一个Name类型的name属性,代表客户的姓名.例1是Name类的源程序.
例1:
从例1看出,Name类是可变类.因此,如果需要修改Customer对象的 name 属性,只需调用Name类的setFirstname()和setLastname()方法:
接下来创建NameCompositeUserType类,它负责把Customer类的Name类型的属性映射到CUSTOMERS表的FIRSTNAME和LASTNAME字段.例2是NameCompositeUserType类的源程序.
例2:
从例2看出,CompositeUserType包含了UserType接口的大部分方法,此外,它还包含了用来访问Name类的所有属性的方法,getPropertyNames(),getPropertyTypes(),getPropertyValue(),setPropertyValue()
在Customer.hbm.xml文件中,以下代码用于把Name类型的name属性映射到CUSTOMERS表的FIRSTNAME和LASTNAME字段:
在应用程序中创建HQL语句时,可以通过"c.name.firstname"的形式访问Customer的name属性的firstname属性:
本文来自****博客,转载请标明出处:http://blog.****.net/lifaming15/archive/2007/06/23/1663786.aspx
Hibernate还提供了一个CompositeUserType借口,它不仅能完成和UserType相同的功能,而且还提供了对Hibernate查询语言(HQL)的支持.下面通过例子来介绍CompositeUserType接口的方法.
假定在Customer类中包含了一个Name类型的name属性,代表客户的姓名.例1是Name类的源程序.
例1:
package mypack; import java.io.Serializable; /** * @author lfm * */ public class Name implements Serializable { private String firstname; private String lastName; public Name(String firstname, String lastName) { super(); // TODO 自动生成构造函数存根 this.firstname = firstname; this.lastName = lastName; } public String getFirstname() { return firstname; } public void setFirstname(String firstname) { this.firstname = firstname; } public String getLastName() { return lastName; } public void setLastName(String lastName) { this.lastName = lastName; } public boolean equals(Object o) { if (this == o) return true; if (!(o instanceof Name)) return false; final Name name = (Name) o; return firstname.equals(name.firstname) && lastName.equals(name.lastName); } public int hashCode() { int result; result = (firstname == null ? 0 : firstname.hashCode()); result = 29 * result + (lastName == null ? 0 : lastName.hashCode()); return result; } public String toString() { return lastName + " " + firstname; } }
从例1看出,Name类是可变类.因此,如果需要修改Customer对象的 name 属性,只需调用Name类的setFirstname()和setLastname()方法:
customer.setName(new Name("Lsosan", "Zhang")); //修改Customer对象的name属性 customer.getName().setFirstname("Lsosi"); customer.getName().setLastname("Li");
接下来创建NameCompositeUserType类,它负责把Customer类的Name类型的属性映射到CUSTOMERS表的FIRSTNAME和LASTNAME字段.例2是NameCompositeUserType类的源程序.
例2:
package mypack; import java.io.Serializable; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Types; import net.sf.hibernate.CompositeUserType; import net.sf.hibernate.Hibernate; import net.sf.hibernate.HibernateException; import net.sf.hibernate.engine.SessionImplementor; import net.sf.hibernate.type.Type; /** * @author lfm * */ public class NameCompositeUserType implements CompositeUserType { /** * 返回Name类的所有属性的名字 */ public String[] getPropertyNames() { // TODO 自动生成方法存根 return new String[] { "firstname", "lastname" }; } /** * 返回Name类的所有属性的Hibernate映射类型 */ public Type[] getPropertyTypes() { // TODO 自动生成方法存根 return new Type[] { Hibernate.STRING, Hibernate.STRING }; } /** * 获取Name队形的某个属性的值。参数component代表Name对象,参数property代表属性在Name对象中的位置 */ public Object getPropertyValue(Object component, int property) throws HibernateException { // TODO 自动生成方法存根 Name name = (Name) component; String result; switch (property) { case 0: result = name.getFirstname(); break; case 1: result = name.getLastName(); default: throw new IllegalArgumentException("unknow property: " + property); } return result; } /** * 设置Name对象的某个属性的值。参数component代表Name对象,参数property代表属性在Name对象中的位置,参数value代表属性值 */ public void setPropertyValue(Object component, int property, Object value) throws HibernateException { // TODO 自动生成方法存根 Name name = (Name) component; String nameValue = (String) value; switch (property) { case 0: name.setFirstname(nameValue); break; case 1: name.setLastName(nameValue); default: throw new IllegalArgumentException("unknow property: " + property); } } /** * 设置NameCompositeUserType所映射的Java类:Name类 */ public Class returnedClass() { // TODO 自动生成方法存根 return Name.class; } public boolean equals(Object x, Object y) throws HibernateException { // TODO 自动生成方法存根 if (x == y) return true; if (x == null || y == null) return false; return x.equals(y); } public Object nullSafeGet(ResultSet rs, String[] names, SessionImplementor session, Object owner) throws HibernateException, SQLException { // TODO 自动生成方法存根 if (rs.wasNull()) return null; String firstname = rs.getString(names[0]); String lastname = rs.getString(names[1]); return new Name(firstname, lastname); } public void nullSafeSet(PreparedStatement statement, Object value, int index, SessionImplementor session) throws HibernateException, SQLException { // TODO 自动生成方法存根 if (value == null) statement.setNull(index, Types.VARCHAR); else { Name name = (Name) value; statement.setString(index, name.getFirstname()); statement.setString(index + 1, name.getLastName()); } } /* * (非 Javadoc) * * @see net.sf.hibernate.CompositeUserType#deepCopy(java.lang.Object) */ public Object deepCopy(Object value) throws HibernateException { // TODO 自动生成方法存根 if (value == null) return null; Name name = (Name) value; return new Name(name.getFirstname(), name.getLastName()); } /* * (非 Javadoc) * * @see net.sf.hibernate.CompositeUserType#isMutable() */ public boolean isMutable() { // TODO 自动生成方法存根 return true; } /** * 创建一格序列化的Name对象,Hibernate将把它保存到缓存中 */ public Serializable disassemble(Object value, SessionImplementor session) throws HibernateException { // TODO 自动生成方法存根 return (Serializable) deepCopy(value); } /** * 根据缓存中的序列化的Name对象,重新构建一个Name对象,参数cached代表缓存中的序列化的Name对象 */ public Object assemble(Serializable cached, SessionImplementor session, Object owner) throws HibernateException { // TODO 自动生成方法存根 return deepCopy(cached); } }
从例2看出,CompositeUserType包含了UserType接口的大部分方法,此外,它还包含了用来访问Name类的所有属性的方法,getPropertyNames(),getPropertyTypes(),getPropertyValue(),setPropertyValue()
在Customer.hbm.xml文件中,以下代码用于把Name类型的name属性映射到CUSTOMERS表的FIRSTNAME和LASTNAME字段:
<property name="name" type="mypack.NameCompositeUserType"> <column name="FIRSTNAME" length="15"/> <column name="LASTNAME" length="15"/> </property>
在应用程序中创建HQL语句时,可以通过"c.name.firstname"的形式访问Customer的name属性的firstname属性:
Customer customer = session.find("from Customer as c where c.name.firstname='Tom'");
本文来自****博客,转载请标明出处:http://blog.****.net/lifaming15/archive/2007/06/23/1663786.aspx