Hibernate: 3. hibernate: 3.

Source: Internet
Author: User

Hibernate: 3. hibernate: 3.

Hibernate retrieval Policy

Reprinted Please note: TheViper http://www.cnblogs.com/TheViper

First look at a rough

 

 

 

1. Class Level

Instant retrieval <class lazy = 'false'>; delayed retrieval <class lazy = 'true'>. The default value is delayed retrieval.

If a persistent object is loaded to obtain its attributes, It is retrieved immediately. If it is only used to obtain its reference, it is loaded with delay. For example,

Friend_Category fc = new Friend_Category (); fc. setCategory_name ("existing friend category"); User_Friend_pk = new User_Friend_pk (); pk. setFriend_name ("New Friend"); pk. setName ("TheViper"); User_Friend uf = new User_Friend (); uf. setUser_friend_pk (pk); Friend_Category fc1 = (Friend_Category) session. load (Friend_Category.class, 1); uf. setFriend_categorys (fc1); // uf. setSort (""); session. saveOrUpdate (fc1); session. save (uf );

We can see that the Friend_Catagory class is loaded only to add new friends to existing friend categories. Here, load () is used to return a proxy class with only the id attribute in it. All other attributes are null, and not all attributes are returned. Therefore, the memory usage is very small.

In addition, whether the lazy attribute of <class> is true or false, get () and list () are always loaded immediately, however, it does not load the associated classes (the associated-level retrieval sets the default delay loading ).

2. association level

  • One-to-many and multiple-to-many associated retrieval policies

Determined by the lazy and fetch attributes of <set>.

Lazy: determines the time when the associated set is initialized. That is, it is initialized during loading or accessed.

Fetch: When the value is select or subselect, it determines the form of the query statement when the associated set is initialized. When the value is fetch, it determines the time when the associated set is initialized, it is meaningless to explicitly set the lazy attribute.

When lazy = true, the proxy associated with the collection class will be initialized in the following situations:

1. The application accesses it for the first time, such as calling its iterator (), size (), isEmpty () or contains ().

2. Perform initialization through the initialize () Static Method of the org. hibernate. Hibernate class.

For lazy = extra, hibernate will further delay the initialization time of the associated object. Specifically, it is loaded only when the application calls the associated object's iterator () for the first time. Only this method works.

For lazy = false,

Feeling f = (Feeling) session.get(Feeling.class, 1);
        <set name="feelingComments" inverse="true" lazy="false">            <key column="feeling_id" />            <one-to-many class="model.FeelingComment" />        </set>

When the Feeling class is taken out, the FeelingComment class is also taken out.

Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?

Set fetch = subselect below,

        Session session = sf.openSession();        Transaction transaction = session.beginTransaction();        Query q = session.createQuery("from Feeling feeling");        List<Feeling> feelings = (List<Feeling>) q.list();        for (Feeling feeling : feelings) {            Set comments = feeling.getFeelingComments();            System.out.println(comments);        }        transaction.commit();        session.close();
Hibernate:     select        feeling0_.feeling_id  as feeling1_1_,        feeling0_.content as content1_,        feeling0_.id as id1_     from        feeling feeling0_Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id in (            select                feeling0_.feeling_id              from                feeling feeling0_        )[model.FeelingComment@17f2fe3, model.FeelingComment@1211a4b, model.FeelingComment@533fc3][model.FeelingComment@a9a994, model.FeelingComment@455d96][model.FeelingComment@35c6f]

We can see that hibernate uses the in subquery method to capture associated objects, and the batch-size attribute is ignored.

Fetch = join indicates that the search policy of the left Outer join is used to capture associated objects. Note that list () automatically ignores this setting, which is very important.

Or the above Code, the result

Hibernate:     select        feeling0_.feeling_id  as feeling1_1_,        feeling0_.content as content1_,        feeling0_.id as id1_     from        feeling feeling0_Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@1fbf047, model.FeelingComment@82a092, model.FeelingComment@15bd7c5]Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@c407e, model.FeelingComment@5e3212]Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@69757f]

In this case, setting the lazy and batch-size attributes is meaningless.

The batch-size attribute is used to set the number of batch queries for the search policy, which can reduce the number of select statements and provide the search running performance.

For example, if the batch-size is set to 2, the associated set contains three objects.

        Session session = sf.openSession();        Transaction transaction = session.beginTransaction();        Query q = session.createQuery("from Feeling feeling");        List<Feeling> feelings = (List<Feeling>) q.list();        for (Feeling feeling : feelings) {            Set comments = feeling.getFeelingComments();            System.out.println(comments);        }        transaction.commit();        session.close();
Hibernate:     select        feeling0_.feeling_id  as feeling1_1_,        feeling0_.content as content1_,        feeling0_.id as id1_     from        feeling feeling0_Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id in (            ?, ?        )[model.FeelingComment@177151, model.FeelingComment@16e125, model.FeelingComment@110a0ca]Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@1c8f247, model.FeelingComment@1d67998][model.FeelingComment@ac44e3]

Note: If you use iterator () to return data for the Query interface, the batch-size will be ignored!

Hibernate:     select        feeling0_.feeling_id  as col_0_0_     from        feeling feeling0_Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@ee7d2a, model.FeelingComment@fb3758, model.FeelingComment@17596bc]Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@855e17]Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?[model.FeelingComment@85ba73, model.FeelingComment@191bae7]

Iterator () See the previous description.

  • Multiple-to-one and one-to-one Retrieval Strategies

 

Fetch = join

        <set name="feelingComments" inverse="true">            <key column="feeling_id" />            <one-to-many class="model.FeelingComment" />        </set>
        <many-to-one name="feelings" column="feeling_id" class="model.Feeling"            not-null="false" fetch="join">        </many-to-one>
        FeelingComment f = (FeelingComment) session                .get(FeelingComment.class, 1);
Hibernate:     select        feelingcom0_.feelingComment_id  as feelingC1_2_1_,        feelingcom0_.content as content2_1_,        feelingcom0_.feeling_id as feeling3_2_1_,        feelingcom0_.id as id2_1_,        feeling1_.feeling_id  as feeling1_1_0_,        feeling1_.content as content1_0_,        feeling1_.id as id1_0_     from        feeling_comment feelingcom0_     left outer join        feeling feeling1_             on feelingcom0_.feeling_id=feeling1_.feeling_id      where        feelingcom0_.feelingComment_id =?

The above is very simple. Change the value by adding lazy = false in <set>.

Hibernate:     select        feelingcom0_.feelingComment_id  as feelingC1_2_1_,        feelingcom0_.content as content2_1_,        feelingcom0_.feeling_id as feeling3_2_1_,        feelingcom0_.id as id2_1_,        feeling1_.feeling_id  as feeling1_1_0_,        feeling1_.content as content1_0_,        feeling1_.id as id1_0_     from        feeling_comment feelingcom0_     left outer join        feeling feeling1_             on feelingcom0_.feeling_id=feeling1_.feeling_id      where        feelingcom0_.feelingComment_id =?Hibernate:     select        feelingcom0_.feeling_id as feeling3_1_1_,        feelingcom0_.feelingComment_id  as feelingC1_1_,        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feeling_id=?

As you can see, two SQL statements are sent this time, and the feeling_comment will be retrieved again based on feeling_id for the second time. I personally feel meaningless. This does not happen in one-to-many and many-to-many scenarios.

In addition, list () will be like one-to-many and many-to-many, ignoring fetch = join.

 

Lazy = proxy (default)

This is like lazy = true in one-to-many and many-to-many. That is, when querying the "multiple" side, the associated objects in the "one" side are not queried. It is initialized only when an associated object is used.

Note that for <one-to-one>, you must set constrained = true, indicating that the correlated object on the "1" side cannot be empty.

 

Lazy = no-proxy

This is very similar to lazy = proxy. However, the bytecode needs to be enhanced during compilation, otherwise it is no different from the proxy.

The effect after this is done.

        FeelingComment f = (FeelingComment) session                .get(FeelingComment.class, 1);        Feeling f1 = f.getFeelings();        f1.getContent();

When getFeelings () is run, hibernate sends an SQL statement. When lazy = proxy is run, it is sent only when getContent () is run.

 

Lazy = false

When running to get (), two SQL statements are sent.

Hibernate:     select        feelingcom0_.feelingComment_id  as feelingC1_2_0_,        feelingcom0_.content as content2_0_,        feelingcom0_.feeling_id as feeling3_2_0_,        feelingcom0_.id as id2_0_     from        feeling_comment feelingcom0_     where        feelingcom0_.feelingComment_id =?Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?

If

        <many-to-one name="feelings" column="feeling_id" class="model.Feeling"            not-null="false" lazy="false">

At the same time

    <class name="model.Feeling" table="feeling" lazy="false">    </class>

The SQL statement is the same as fetch = join.

        FeelingComment f = (FeelingComment) session                .get(FeelingComment.class, 1);
Hibernate:     select        feelingcom0_.feelingComment_id  as feelingC1_2_1_,        feelingcom0_.content as content2_1_,        feelingcom0_.feeling_id as feeling3_2_1_,        feelingcom0_.id as id2_1_,        feeling1_.feeling_id  as feeling1_1_0_,        feeling1_.content as content1_0_,        feeling1_.id as id1_0_     from        feeling_comment feelingcom0_     left outer join        feeling feeling1_             on feelingcom0_.feeling_id=feeling1_.feeling_id      where        feelingcom0_.feelingComment_id =?

 

 

Use batch search in many-to-one and one-to-one scenarios

In <batch-to-one>, <one-to-one>, there is no batch-size attribute. You need to set batch-size for "1. for example, you need to add three associated instances (1), batch-size = 2.

    <class name="model.Feeling" table="feeling" batch-size="2">    </class>
        Query q = session.createQuery("from FeelingComment");        List<FeelingComment> feelings = (List<FeelingComment>) q.list();        for (FeelingComment feelingComment : feelings) {            Feeling feeling = feelingComment.getFeelings();            System.out.println(feeling);        }
Hibernate:     select        feelingcom0_.feelingComment_id  as feelingC1_2_,        feelingcom0_.content as content2_,        feelingcom0_.feeling_id as feeling3_2_,        feelingcom0_.id as id2_     from        feeling_comment feelingcom0_Hibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id  in (            ?, ?        )model.Feeling@1e684bdmodel.Feeling@1e684bdmodel.Feeling@1e684bdmodel.Feeling@1149b6cHibernate:     select        feeling0_.feeling_id  as feeling1_1_0_,        feeling0_.content as content1_0_,        feeling0_.id as id1_0_     from        feeling feeling0_     where        feeling0_.feeling_id =?model.Feeling@fb8996model.Feeling@1149b6c

Note that the lazy in the above example is the default proxy. if lazy = false, run the command to feelingComment. getFeelings (); then the subsequent SQL statement is sent.

 

  • Attribute-level retrieval Policy

You only need to set lazy = true on <property> and <component>. This policy applies to attributes of Binary large objects, string large objects, and large-capacity component types. For example, the image attribute of the User class stores the binary data of the image,

User user = (User) session. get (User. class, 1); user. getImage ();

When get () is run, hibernate does not load the image attribute. It is loaded only when it is run to getImage.

Note: When using this function, you must use multiple-to-one, one-to-one lazy = no-proxy, and the bytecode needs to be enhanced during compilation.

 

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.