2017-06-22 5 views
0
@Entity 
@Table(name = "STUDENT") 
public class Student { 

    private long studentId; 
    private String studentName; 
    private List<Phone> studentPhoneNumbers; 

    .... 

    @OneToMany(cascade = CascadeType.ALL) 
    @JoinTable(name = "STUDENT_PHONE", joinColumns = { @JoinColumn(name = "STUDENT_ID") }, inverseJoinColumns = { @JoinColumn(name = "PHONE_ID") }) 
    public List<Phone> getStudentPhoneNumbers() { 
     return this.studentPhoneNumbers; 
    } 

    public void setStudentPhoneNumbers(List<Phone> studentPhoneNumbers) { 
     this.studentPhoneNumbers = studentPhoneNumbers; 
    } 
} 

1)Hibernate OneToManyリストまたはIteratorが異なる?

Student student = session.loadStudent(123); // pseudocode 
List phoneList = student.getStudentPhoneNumbers(); 
for (Phone p : phoneList) { 
    ... 
} 

2)

Student student = session.loadStudent(123); // pseudocode 
List phoneList = student.getStudentPhoneNumbers(); 
Iterator itr = phoneList.iterator(); 
while(itr.hasNext()) { 
    ... 
} 

私はここからの回答をお読みください。difference between query.list and query.iterate

明らかlist()iterator()()Queryで違いがあります。 OneToManyのリストで使用するとどうなりますか?上記の例のように、パフォーマンスの点で違いがありますか?メモリ?

+0

@Scary Wombat、この質問はどのように重複していますか? Hibernateは暗黙的にプロキシを作成して 'List'オブジェクトをラップし、これらの2つのメソッドを呼び出すことは異なる影響を与えるかもしれません。 – GMsoF

+0

投稿したコードの2つのスニペットはまったく同じことを行います。最初のスニペットのforeachループは、2番目のスニペットのように、シーンの背後にあるList.iterator()を使用します。それはHibernateとは関係ありません。 –

答えて

-1

私はこのHibernate chapterを読んで、プロキシのパフォーマンスを詳しく説明しています。

エンティティのマッピングFetchTypeはデフォルトでlazyです。これは、hibernateが属性の周囲にプロキシを作成します。

list.size()(など)を呼び出すと、hibernateはすべての子オブジェクトをロードし始めます。

すべてを読み込みたくない場合は、extra lazyという新しい機能を使用できます。特定のレコードのみに対してselectステートメントを発行します。たとえば、list.get(3)は4行目のみを選択します。

アトリビュートにeagerと注釈を付けると、hibernateは、親オブジェクトをロードすると、すべての子オブジェクトをロードします(重複した問題を持つ外部ジョインを使用します)。この場合、属性を囲むプロキシはありません。パフォーマンスの差はありません。listまたはiteratorとして使用しても問題ありません。

+0

遅延フェッチプロキシについて書いたものは正しいですか?しかし、あなたのオリジナルの質問には*** ***は適用されません。あなたの質問では、for-eachループとiteratorを使ってコレクションを反復するように求めています。遅延プロキシがここで違いを生むものは何もありません。 –

+0

ええ、それは私の間違いでした。私は気づいていませんでした。それぞれとイテレータは同じものです。私のサンプルコードはちょっと混乱しています。実際には、アイテムを1つずつリスト全体またはリスト全体で取得する方法を探していました、パフォーマンスを比較します。時間があれば私の質問を編集します。ありがとうございます。 – GMsoF

+0

あなたが言ったことはまだ間違っています。あなたの答えは「1つ1つ」対「全体リスト」とは関係ありません。レイジーコレクションプロキシはアクセス時にリスト全体を取得しようとしています –

1

これはHibernateとは関係ありません。 Javaコンパイラは

for (Phone p : phoneList) { 
    .... 
} 

に遭遇すると

それが自動的だから、基本的にあなたが表示される二つの例でも同じです

for (Iterator<Phone> itr = phoneList.iterator(); itr.hasNext();) { 
    Phone p = itr.next(); 
    .... 
} 

へのコードと同等を生成します。

関連する問題