These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 
Author Message
 Post subject: Need optimization suggestions for lazily initialized collect
PostPosted: Thu Jul 29, 2010 4:56 am 
Newbie

Joined: Thu Jul 29, 2010 3:59 am
Posts: 1
Hello, folks! I need optimization suggestions for lazily initialized collections. I will first describe the code, then the problem. Any help is greatly appreciated!

***

Situation details

@Entity
public class User
{
@Id
@Column(name = "USER_ID", nullable = false, precision = 20)
private Long id;

@OneToMany(mappedBy = "user", fetch = FetchType.LAZY, cascade = CascadeType.ALL)
@BatchSize(size = 10)
private Set<Vote> votes;
}

@Entity
public class Product
{
@Id
@Column(name = "PRODUCT_ID", nullable = false, precision = 20)
private Long id;

@OneToMany(mappedBy = "product", fetch = FetchType.LAZY, cascade = CascadeType.ALL)
@BatchSize(size = 10)
private Set<Vote> votes;
}

@Entity
public class Vote
{
@Id
@Column(name = "VOTE_ID", nullable = false, precision = 20)
private Long id;

@Column(name = "CASTED_VOTE", precision = 3, scale = 2, columnDefinition = "NUMBER(3,2)")
private Double castedVote;

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "USER_ID_REF")
private User user;

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "PRODUCT_ID_REF")
private Product product;
}

Essentially, Vote is an association table between User and Product in a many-to-many bidirectional relationship (@ManyToMany annotation cannot be used though because there are other columns in the Vote table, namely, CASTED_VOTE).

For example, we have two Users, "Ivanoff" and "Petroff", and two Products, "Balalaika" and "Vodka". Each user casts votes for every product, so we have four votes total, { vote1, vote2, vote3, vote4 }:

Ivanoff.votes = { vote1, vote2 }
Petroff.votes = { vote3, vote4 }

Balalaika.votes = { vote1, vote3 }
Vodka.votes = { vote2, vote4 }

***

Problem details

When I access User#votes, it is lazily initialized. The Select to the database looks as such (simplified for easier understanding):

select vote0_.VOTE_ID, ... blah-blah-blah... from VOTE vote0_ where vote0_.USER_ID_REF in (?, ?)

Similarly, when I access Product#votes, the Select to the database looks as such:

select vote0_.VOTE_ID, ... blah-blah-blah... from VOTE vote0_ where vote0_.PRODUCT_ID_REF in (?, ?)

So, two different selects are performed to initialize the same objects. When I have initialized one of the lazy associations I want to be able to load at least some of the elements of the second lazy association from the cache, not from the database. When I use the batch fetching mode for the votes and iterate through all the users, every possible vote row there is is initialized. Then, when I iterate through all the products, the votes are initialized from the database again, not from the cache. Collection of users is relatively small, collection of products is vast. It is crucial for me that only one select to the database is performed. How can I solve this problem?


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 1 post ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.