论坛首页 入门技术论坛

[求教]为什么我在使用HashCodeBuilder在one-to-many关系中出现Lazy异常

浏览 5146 次
该帖已经被评为新手帖
作者 正文
   发表时间:2007-02-02  
最近遇到一个奇怪的问题,我在实体类的基类中使用了org.apache.commons.lang.builder.HashCodeBuilder,然后在one-to-many关系映射(customer <---> order)中出现org.hibernate.LazyInitializationException: illegal access to loading collection异常。

小弟刚刚接触hibernate,这个问题找了两天才发现问题所在,但是仍然不知道为什么会这样,请大家不吝赐教。

环境:struts + hibernate3,  hibernate2也试验过
异常:
org.hibernate.LazyInitializationException: illegal access to loading collection
at org.hibernate.collection.AbstractPersistentCollection.initialize(AbstractPersistentCollection.java:341)
at org.hibernate.collection.AbstractPersistentCollection.read(AbstractPersistentCollection.java:86)
at org.hibernate.collection.PersistentSet.hashCode(PersistentSet.java:411)
at org.apache.commons.lang.builder.HashCodeBuilder.append(HashCodeBuilder.java:392)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionAppend(HashCodeBuilder.java:353)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionHashCode(HashCodeBuilder.java:327)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionHashCode(HashCodeBuilder.java:194)
at cz.model.BaseObject.hashCode(BaseObject.java:78)
at org.apache.commons.lang.builder.HashCodeBuilder.append(HashCodeBuilder.java:392)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionAppend(HashCodeBuilder.java:353)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionHashCode(HashCodeBuilder.java:327)
at org.apache.commons.lang.builder.HashCodeBuilder.reflectionHashCode(HashCodeBuilder.java:194)
at cz.model.BaseObject.hashCode(BaseObject.java:78)
at java.util.HashMap.hash(HashMap.java:261)...

Hibernate 3 和 2 都是这个异常
只是2的异常描述是:net.sf.hibernate.LazyInitializationException: cannot access loading collection

程序片断:
BO基类 cz.model.BaseObject


abstract public class BaseObject implements Serializable {	
	public BaseObject(){}
    ...	
    public String toString() {
        return ToStringBuilder.reflectionToString(this,
                ToStringStyle.MULTI_LINE_STYLE);
    }

    public boolean equals(Object o) {
        return EqualsBuilder.reflectionEquals(this, o);
    }

    //注释掉这个函数就不出现异常
    public int hashCode() {
        return HashCodeBuilder.reflectionHashCode(this);
    }

cz.model.Customer继承BaseObject
public class Customer extends BaseObject implements Serializable {
      ...
	}

cz.model.Order继承BaseObject
public class Order extends BaseObject implements Serializable {
      ...
	}

映射文件

Customer.hbm.xml
<?xml version="1.0" encoding='UTF-8'?>
<!DOCTYPE hibernate-mapping PUBLIC
                            "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
                            "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd" >
<hibernate-mapping>

    <class name="cz.model.Customer" table="CUSTOMERS">
        <id name="id" column="ID" type="long">
            <generator class="increment"/>
        </id>
      ...
    <set 
        name="orders"
        cascade="all-delete-orphan" 
        inverse="true"
        lazy="true">
        <key column="CUSTOMER_ID" />
        <one-to-many class="cz.model.Order"/>
     </set>  
    </class>
    
</hibernate-mapping>

Order.hbm.xml
<hibernate-mapping>

	<class name="cz.model.Order" table="ORDERS">

		<id name="id" type="long" column="ID">
			<generator class="increment" />
		</id>
                  ....
		<many-to-one name="customer" column="CUSTOMER_ID"
			class="cz.model.Customer" cascade="save-update"/>
	</class>
</hibernate-mapping>

DAO实现类中的方法
	public Customer getCustomerById(Long customerId) throws AppException {

		Session session = HibernateUtil.getSession();
		Transaction tx = null;
		try {
			tx = session.beginTransaction();
			Query query = session.createQuery("from Customer c where c.id=:id");
			query.setLong("id", customerId.longValue());
			Customer customer = (Customer)query.uniqueResult();
			Set orderset = customer.getOrders();


                            //在这里会抛出上面说的异常,如果在BaseObject.java中去掉
                                 //public int hashCode() 方法就会正常,这是为什么呢??
			System.out.println("orderset size=" + orderset.size());

			tx.commit();

			return customer;

		} catch (Exception ex) {
			HibernateUtil.rollbackTransaction(tx);
			AppException.appError(ex).printStackTrace();
			throw AppException.appError(ex);
		} finally {
			
			HibernateUtil.closeSession(session);
		}
	}


请大家帮我解答一下这个问题,谢谢。





   发表时间:2007-02-07  
遇到类似的问题,请教高手
0 请登录后投票
   发表时间:2007-02-16  
我也遇到了,这个问题
0 请登录后投票
   发表时间:2007-03-14  
可以自己实现HashCodeBuilder

java 代码
 
  1. import java.lang.reflect.Array;  
  2.   
  3. public class HashCodeBuilder {  
  4.     public HashCodeBuilder() {  
  5.   
  6.     }  
  7.   
  8.     private int result = 17;  
  9.   
  10.     public HashCodeBuilder append(boolean field) {  
  11.         result = 37 * result + (field ? 1 : 0);  
  12.         return this;  
  13.     }  
  14.   
  15.     public HashCodeBuilder append(byte field) {  
  16.         result = 37 * result + (int) field;  
  17.         return this;  
  18.     }  
  19.   
  20.     public HashCodeBuilder append(char field) {  
  21.         result = 37 * result + (int) field;  
  22.         return this;  
  23.     }  
  24.   
  25.     public HashCodeBuilder append(short field) {  
  26.         result = 37 * result + (int) field;  
  27.         return this;  
  28.     }  
  29.   
  30.     public HashCodeBuilder append(int field) {  
  31.         result = 37 * result + field;  
  32.         return this;  
  33.     }  
  34.   
  35.     public HashCodeBuilder append(long field) {  
  36.         result = 37 * result + (int) (field ^ (field >>> 32));  
  37.         return this;  
  38.     }  
  39.   
  40.     public HashCodeBuilder append(float field) {  
  41.         result = 37 * result + Float.floatToIntBits(field);  
  42.         return this;  
  43.     }  
  44.   
  45.     public HashCodeBuilder append(double field) {  
  46.         append(Double.doubleToLongBits(field));  
  47.         return this;  
  48.     }  
  49.   
  50.     public HashCodeBuilder append(Object field) {  
  51.         if(field == null)  
  52.             result = 0;  
  53.         else if (field.getClass().isArray()) {  
  54.             for (int i = Array.getLength(field) - 1; i >= 0; i--) {  
  55.                 append(Array.get(field, i));  
  56.             }  
  57.         } else  
  58.             append(field.hashCode());  
  59.         return this;  
  60.     }  
  61.   
  62.     public int toHashCode() {  
  63.         return result;  
  64.     }  
  65.       
  66.     @Override  
  67.     public int hashCode() {  
  68.         return result;  
  69.     }  
  70.       
  71.     @Override  
  72.     public String toString() {  
  73.         return String.valueOf(result);  
  74.     }  
  75.   
  76. }  
0 请登录后投票
论坛首页 入门技术版

跳转论坛:
Global site tag (gtag.js) - Google Analytics