Hibernate---Performance optimization, 1+n problems

Source: Internet
Author: User

Session cache Save a HashMap, read out the object is placed in the inside, if read out 50 to put 50, if another session of the original 50 is cleared. You can session.clear the purge manually.

If the same session is read all the time, there is more and more memory. So use Session.clear () to handle it.

Is there a memory leak in Java? Not syntactically, but when you write a program, you use resources to recycle, such as opening a connection pool.

1+n problem: If an object is associated with another object, and Fetchtype is eager, such as many to one, when the object is taken many, the associated object will be taken out, and the 1+n bar will be taken out.

When getting the contents of topic, the category of the associated object is also taken out:

Category.java:

Package Com.bjsxt.hibernate;import Javax.persistence.entity;import Javax.persistence.generatedvalue;import Javax.persistence.id;import org.hibernate.annotations.BatchSize; @Entity//@BatchSize (size=5) public class Category { private int id;private String name; @Id @generatedvaluepublic int getId () {return ID;} public void setId (int id) {this.id = ID;} Public String GetName () {return name;} public void SetName (String name) {this.name = name;}}

Topic.java:

Package Com.bjsxt.hibernate;import Java.util.arraylist;import Java.util.date;import java.util.list;import Javax.persistence.entity;import Javax.persistence.fetchtype;import Javax.persistence.generatedvalue;import Javax.persistence.id;import Javax.persistence.manytoone;import Javax.persistence.namedqueries;import Javax.persistence.namedquery;import Javax.persistence.onetomany;import org.hibernate.annotations.batchsize;@ Entity@namedqueries ({@NamedQuery (name= "Topic.selectcertaintopic", query= "from topic t where T.id =: id")})/*@ Namednativequeries ({@NamedNativeQuery (name= "Topic.select2_5topic", query= "SELECT * from topic limit 2, 5")}) */public Class Topic {private int id;private String title;private Category category;private Date createdate;private list<msg&gt ; msgs = new Arraylist<msg> (), @OneToMany (mappedby= "topic") Public list<msg> Getmsgs () {return msgs;} public void Setmsgs (list<msg> msgs) {this.msgs = msgs;} Public Date Getcreatedate () {return createdate;} public void Setcreatedate (Date createdate) {this.createdate = CreateDate;} @ManyToOnepublic category GetCategory () {return category;} public void Setcategory (category category) {this.category = category;} @Id @generatedvaluepublic int getId () {return Id;} public void setId (int id) {this.id = ID;} Public String GetTitle () {return title;} public void Settitle (String title) {this.title = title;}}

Msg.java:

Package Com.bjsxt.hibernate;import Javax.persistence.entity;import Javax.persistence.generatedvalue;import Javax.persistence.id;import Javax.persistence.ManyToOne; @Entitypublic class MSG {private int id;private String cont; Private Topic Topic; @ManyToOnepublic Topic gettopic () {return Topic;} public void Settopic (Topic Topic) {this.topic = Topic;} @Id @generatedvaluepublic int getId () {return Id;} public void setId (int id) {this.id = ID;} Public String Getcont () {return cont;} public void Setcont (String cont) {this.cont = cont;}}

Hibernate.cfg.xml:

<?xml version='1.0'encoding='Utf-8'? ><! DOCTYPE hibernate-Configuration Public"-//hibernate/hibernate Configuration DTD 3.0//en"        "HTTP://HIBERNATE.SOURCEFORGE.NET/HIBERNATE-CONFIGURATION-3.0.DTD">"Connection.driver_class">com.mysql.jdbc.Driver</property> <property name="Connection.url">jdbc:mysql://localhost/hibernate</property><property name="Connection.username">root</property> <property name="Connection.password">linda0213</property> <property name="dialect">org.hibernate.dialect.MySQLDialect</property> <!--<property name="Connection.driver_class">oracle.jdbc.driver.OracleDriver</property> <property name="Connection.url">jdbc:oracle:thin: @localhost:1521:sxt</property> <property name="Connection.username">scott</property> <property name="Connection.password">tiger</property> <property name="dialect">org.hibernate.dialect.OracleDialect</property>-<!--JDBC Connection pool (use the built-inch)-<property Name="connection.pool_size">1</property> <!--Enable Hibernate's automatic session context management --<property name="Current_session_context_class">thread</property> <!--Disable the Second-level Cache--and <property name="Cache.provider_class">org.hibernate.cache.NoCacheProvider</property> <!--Echo all executed-SQL to stdout--< Property Name="Show_sql">true</property> <property name="Format_sql">true</property> <!--Drop and re-Create the database schema on startup<property name="Hbm2ddl.auto">update</property> <!--<mapping resource="Com/bjsxt/hibernate/group.hbm.xml"/> <mapping resource="Com/bjsxt/hibernate/user.hbm.xml"/>-<mappingclass="com.bjsxt.hibernate.Category"/> <mappingclass="COM.BJSXT.HIBERNATE.MSG"/> <mappingclass="Com.bjsxt.hibernate.Topic"/> </session-factory>

Test file:

Package Com.bjsxt.hibernate;import Java.util.date;import Java.util.list;import org.hibernate.session;import Org.hibernate.sessionfactory;import Org.hibernate.cfg.annotationconfiguration;import Org.hibernate.tool.hbm2ddl.schemaexport;import Org.junit.afterclass;import Org.junit.beforeclass;import Org.junit.test;public class Hibernateqltest {private static sessionfactory sf; @BeforeClasspublic static void Beforeclass () {SF = new annotationconfiguration (). Configure (). Buildsessionfactory (); @AfterClasspublic static void Afterclass () {sf.close ();} @Testpublic void Testschemaexport () {New Schemaexport (new Annotationconfiguration (). Configure ()). Create (False, True) ;} @Testpublic void Testsave () {Session session = Sf.opensession (); Session.begintransaction (); for (int i=0; i<10; i++) { Category C = new category (); C.setname ("C" + i); Topic t = new Topic (), t.setcategory (c); T.settitle ("T" + i); T.setcreatedate (new Date ()); Session.save (c); Session.save (t );} Session.gettransaction (). commit (); Session.close ();} n+1@testpublic void TestQuery1 () {Session session = Sf.opensession (); Session.begintransaction ();//list<topic > topics = (list<topic>) Session.createcriteria (Topic.class). List (); list<topic> topics = (list<topic>) session.createquery ("from Topic"). List (); for (Topic t:topics) {System.out.println (T.getid () + "-" + t.gettitle ());} Session.gettransaction (). commit (); Session.close ();} @Testpublic void TestQuery2 () {Session session = Sf.opensession (); Session.begintransaction ();//list<topic> Topics = (list<topic>) Session.createcriteria (Topic.class). List (); list<topic> topics = (list<topic>) session.createquery ("from Topic"). List (); for (Topic t:topics) {System.out.println (T.getid () + "-" + t.gettitle ()); System.out.println (T.getcategory (). GetName ());} Session.gettransaction (). commit (); Session.close ();} @BatchSize @testpublic void TestQuery3 () {Session session = Sf.opensession (); Session.begintransaction ();//list< topic> topics = (list<topic>) Session.createcriteria (topic.class). List (); list<topic> topics = (list<topic>) session.createquery ("from Topic"). List (); for (Topic T:topics) { System.out.println (T.getid () + "-" + t.gettitle ()); System.out.println (T.getcategory (). GetName ());} Session.gettransaction (). commit (); Session.close ();} Join Fetch@testpublic void TestQuery4 () {Session session = Sf.opensession (); Session.begintransaction ();//list< topic> topics = (list<topic>) Session.createcriteria (Topic.class). List (); list<topic> topics = (list<topic>) session.createquery ("from Topic T left join fetch t.category C"). List (); for (Topic t:topics) {System.out.println (T.getid () + "-" + t.gettitle ()); System.out.println (T.getcategory (). GetName ());} Session.gettransaction (). commit (); Session.close ();} public static void Main (string[] args) {beforeclass ();}}

At this point the output will print out the category's query information in passing,

Hibernate:select topic0_.id as Id2_, topic0_.category_id as category4_2_, topic0_.createdate as Createdate2_, Topic0_.title as title2_ from Topic topic0_hibernate:select category0_.id as I d0_0_, Category0_.name as name0_0_ from Category category0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:selECT category0_.id as id0_0_, category0_.name as name0_0_ from Category category0_ where Category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where category0_.id=? Hibernate:select category0_.id as id0_0_, category0_.name as name0_0_ from category category 0_ where Category0_.id=?1-t02-t13-t24-t35-t46-t57-t68-t79-t810-t9

Solution Solutions

1. Write Fetch=fetchtype.lazy many to one in Topic.java

2. Replace query with Creteria in the test file. Because Creteria is the way of table joins, and 41 like.

3. In the category @entity add @BatchSize (size=5), so that 10 records, 2 SQL will be issued.

4, using join Fetch:

Join Fetch@testpublic void TestQuery4 () {Session session = Sf.opensession (); Session.begintransaction ();//list< topic> topics = (list<topic>) Session.createcriteria (Topic.class). List (); list<topic> topics = (list<topic>) session.createquery ("from Topic T left join fetch t.category C"). List (); for (Topic t:topics) {System.out.println (T.getid () + "-" + t.gettitle ()); System.out.println (T.getcategory (). GetName ());} Session.gettransaction (). commit (); Session.close ();}

How do I choose which one to use?

Lazy: Takes object properties, does not take properties of associated objects

Join fetch: Immediately with the properties of the associated object

Hibernate---Performance optimization, 1+n problems

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.