2011-11-07 21 views
1

レイジーローディングに関するいくつかのテストを試みている間に、私がそれをよく理解しているかどうかを確認するために、私は完全に混乱しました。ここでレイジーローディングについて混乱しています

は私が私のテストに使用していたエンティティです:、私は遅延ロードから理解何

public static void main(String[] args) { 
    factory = Persistence.createEntityManagerFactory(PERSISTENCE_UNIT_NAME); 
    em = factory.createEntityManager(); 

    Query q = em.createQuery("select f from Family f"); 
    List<Family> families= q.getResultList(); 

    em.clear(); 
    em.close(); 
    factory.close(); 

    for(Family f:families){ 
     System.out.println(f); 
    } 
} 

かの属性がマークされていることである。

@Entity 
public class Family { 
@Id 
private int id; 


@OneToMany(mappedBy="family", fetch=FetchType.LAZY) 
private Set<Person> members; 

//getters & setters 

public String toString(){ 
    String s=""; 
    for(Person p:getMembers()){ 
     s+=p.getFirstName(); 
    } 
    return s; 
} 
} 

@Entity 
public class Person implements Comparable<Person>{ 
@Id 
private int id; 

private String firstName; 
private String lastName; 

@ManyToOne 
private Family family; 

//getters &setters 
} 

ここに私の主な方法です遅延してフェッチされ、管理されている間はアクセスされません。メモリにロードされず、後でアクセスしようとしても機能しません。今私が混乱しているのは、EMとEMFを閉じた後でも、分離されたファミリーリストから遅延メンバー属性にアクセスする際に、上記のテストが問題にならないことです! ...それは普通ですか?私は怠惰なローディングの概念を理解していませんか?

注:私は組み込みDBを備えたJ2SE環境を使用しています。私のプロバイダはJPAプロバイダが遅延初期化を使用する必要はありませんので、それはあるかもしれないアドバンス
ジョージ

答えて

2

エンティティがログに記録されているなど、工場が閉じられる前にtoStringメソッドがトリガーされていないことを確認してください。これはエラーが発生しやすく、予期せずトリガーされる可能性があるため、toStringメソッドでトリガー関係をトリガーすることはお勧めしません。 EclipseLinkのロギングを有効にすると、問題の一部ではないことを前提に、工場のライフサイクルでどこにアクセスするのかがわかります。

+0

私はすでにあなたの答えを[ //www.eclipse.org/forums/index.php/mv/msg/261691/755570/#msg_755570):-) –

0

でのEclipseLink

おかげです。 JPAプロバイダの必須要件ではありませんが、a hintです。

FetchType.EAGERが指定されている場合、JPAはデータを熱心に取得する必要がありますが、FetchType.LAZYが指定されている場合は、データを遅延取得する必要はありません。

+0

お返事ありがとうございます。私のJPAプロバイダがEclipseLinkであることは忘れてしまいました.PlayLinkは、遅延ロードAFAIKをサポートしています。 –

2

eclipselinkエージェントを使用していること、または静的織りを使用していることを確認してください。どちらも使用していない場合、LAZYは製織されず、EAGERを取得します。

また、EclipseLinkは、EntityManagerが閉じられた後にLAZY関係へのアクセスをサポートします。 工場は閉鎖されていませんが。しかし、オブジェクトがキャッシュ内にあった場合、オブジェクトは閉じられた後にも動作する可能性があります。また、同じパーシスタンスユニットで別のファクトリを開いている場合、パーシスタンスユニットはまだ開いています。

+0

私は[ここ](http://www.eclipse.org/forums/index.php/mv/tree/160098/#page_top)で同様の質問を見つけました。答えがありました。 「実際に織っているのは、怠惰なOneToOne/ManyToOneの怠惰に必要なのは、織り合わせることなくOneToManyで動作する」というJames氏の言葉です。これは[ここ](http://wiki.eclipse.org)で確認されています。/Using_EclipseLink_JPA_Extensions_%28ELUG%29#What_You_May_Need_to_Know_About_EclipseLink_JPA_Lazy_Loading)。 –

+0

EntityManegrが閉じられた後にLAZY関係にアクセスするためのサポートについては、私はこれをむしろ利点としてconcidingするので、問題はありません...私はちょうど私が怠惰な関係にアクセスしない場合、メモリにロードされないと確かにこれは起こっていないことを保証したいと思います。工場を閉じた後でも(これは私の例で試したときにユニークです)家族のインスタンスはまだメンバーにアクセスすることができ、上記のように、私は工場を閉鎖する前にそれらのいずれにもアクセスしませんでした:( –

関連する問題