2010-02-03 18 views

risposta

240

Supponiamo che tu abbia un genitore e che il genitore abbia una collezione di bambini. Hibernate ora può "caricare pigro" i bambini, il che significa che in realtà non carica tutti i bambini durante il caricamento del genitore. Invece, li carica quando richiesto per farlo. Puoi richiederlo esplicitamente oppure, e questo è molto più comune, l'ibernazione li carica automaticamente quando provi ad accedere ad un bambino.

Il caricamento lento può aiutare a migliorare significativamente le prestazioni poiché spesso non sono necessari i bambini e pertanto non verranno caricati.

Fate attenzione anche al problema n + 1. Hibernate non caricherà tutti i bambini durante l'accesso alla raccolta. Invece, caricherà ogni bambino individualmente. Durante l'iterazione sulla raccolta, ciò causa una query per ogni bambino. Per evitare questo, puoi ingannare l'ibernazione per caricare tutti i bambini contemporaneamente, ad es. chiamando parent.getChildren(). size().

+0

Bella spiegazione –

+75

che trucco !! parent.getChildren() formato().; +1 –

+3

Alternativamente Hibernate.initialize (parent.getChildren()) dovrebbe essere usato – HakunaMatata

5

Lazy Loading? Bene, significa semplicemente che i record figlio non vengono recuperati immediatamente, ma automaticamente non appena si tenta di accedervi.

2

pigro caricamento è un modello di progettazione comunemente utilizzato nella programmazione di computer rinviare l'inizializzazione di un oggetto fino al punto in cui è necessario. Può contribuire all'efficienza nel funzionamento del programma del se correttamente e opportunamente utilizzati

Wikipedia

link di Lazy Loading da hibernate.org

66

"loading Pigro" significa che un soggetto viene caricato solo quando si in realtà accede all'entità per prima.

Il pattern è come questo:

public Entity getEntity() { 
    if (entity == null) { 
     entity = loadEntity(); 
    } 
    return entity; 
} 

questo consente di risparmiare il costo di precarico/precarica tutti le entità in un grande insieme di dati in anticipo mentre dopo tutto in realtà non è necessario tutte di loro.

In Hibernate, è possibile configurare caricare pigramente una raccolta di entità figlio. Il caricamento lordo effettivo viene quindi eseguito all'interno dei metodi dello PersistentSet che Hibernate utilizza "sotto i cofani" per assegnare la raccolta di entità come Set.

E.g.

public class Parent { 
    private Set<Child> children; 

    public Set<Child> getChildren() { 
     return children; 
    } 
} 

.

public void doSomething() { 
    Set<Child> children = parent.getChildren(); // Still contains nothing. 

    // Whenever you call one of the following (indirectly), 
    // Hibernate will start to actually load and fill the set. 
    children.size(); 
    children.iterator(); 
} 
+0

Ho lo stesso caso e l'ibernazione genera un'eccezione quando si accede a Set children = parent.getChildren(); , c'è una configurazione facoltativa per rendere questo succede – bmscomp

22

Martin Fowler definisce il modello Lazy Load in Patterns of Enterprise Application Architecture come tale:

Un oggetto che non contiene tutti i dati necessari, ma sa come ottenerlo.

Così, quando si carica un determinato oggetto, l'idea è quella di non carico ansiosi l'oggetto relativo (s), che non è possibile utilizzare immediatamente per salvare il relativo costo delle prestazioni. Invece, gli oggetti correlati saranno caricati solo quando usati.

Questo non è un modello specifico per l'accesso ai dati e Hibernate, ma è particolarmente utile in tali campi e Hibernate supporta il caricamento lento di associazioni uno-a-molti e associazioni a punto singolo (one-to-one e many-to -one) anche a determinate condizioni. L'interazione pigra è discussa in modo più dettagliato in Chapter 19 della documentazione di riferimento di Hibernate 3.0.

0

Hiberante supporta la funzionalità di inizializzazione pigra per entrambe le entità e le raccolte. Il motore di ibernazione carica solo gli oggetti per i quali stiamo interrogando non ha altre entrate o collezioni.

pigro = "false" per impostazione predefinita carico di inizializzazione menzione per il figlio unico è caso lazy.in di vero che è genitore è carico non supporta bambino

3

impostazione pigro decide se caricare oggetti figlio durante il caricamento dell'oggetto padre. È necessario eseguire questa impostazione rispettivo file di mappatura in modalità ibernazione della classe genitore. Lazy = true (significa non caricare child) Per impostazione predefinita il caricamento lazy degli oggetti figlio è true. Questo assicura che gli oggetti figlio non vengano caricati a meno che non siano esplicitamente richiamati nell'applicazione chiamando il metodo getChild() su parent.In questo caso hibernate emette una nuova chiamata al database per caricare il figlio quando getChild() viene chiamato actully sul Parent oggetto. Ma in alcuni casi è necessario caricare gli oggetti figlio quando viene caricato il genitore. Basta fare il lazy = false e hibernate caricherà il figlio quando il genitore viene caricato dal database.Exampleslazy = true (default) Address child di User class può essere reso pigro se non è richiesto frequentemente.lazy = falseMa potrebbe essere necessario caricare l'oggetto Autore per Genitore del libro ogni volta che gestisci il libro per la libreria online.

0

L'impostazione Lazy decide se caricare oggetti figlio durante il caricamento dell'oggetto padre. È necessario eseguire questa impostazione il rispettivo file di mapping in modalità ibernazione della classe genitore. Lazy = true (significa non caricare child) Per impostazione predefinita il caricamento lazy del gli oggetti figlio sono veri.

12

Il caricamento lazy di default è vero. Il caricamento lento indica che quando viene eseguita la query di selezione non colpisce il database. Aspetterà la funzione getter, cioè quando avremo richiesto, verrà recuperato dal database. per esempio: Sei un genitore che ha un bambino con un sacco di giocattoli. Ma il problema attuale è che ogni volta che lo chiami (supponiamo che tu abbia un ragazzo), viene da te con tutti i suoi giocattoli. Ora questo è un problema dal momento che non vuoi che si porti dietro i suoi giocattoli tutto il tempo. Quindi, essendo il genitore razionale, vai avanti e definisci i giocattoli del bambino come LAZY. Ora ogni volta che lo chiami, viene da te senza i suoi giocattoli.

+3

Questa è una bella analogia – Siddhartha

7

Il recupero pigro decide se caricare oggetti figlio durante il caricamento dell'oggetto padre. È necessario eseguire questa impostazione rispettivo file di mappatura di ibernazione della classe genitore. Lazy = true (significa non caricare il child) Per impostazione predefinita il caricamento lento degli oggetti figli è vero.

Questa assicurarsi che gli oggetti figlio non vengono caricati meno che non siano esplicitamente invocati nella richiesta chiamando getChild() metodo su parent.In questo caso hibernate emette una chiamata al database fresca per caricare il bambino quando si getChild() actully chiamati Capogruppo oggetto.

Ma in alcuni casi è necessario caricare gli oggetti figlio quando viene caricato il genitore. Basta fare il lazy = false e hibernate caricherà il bambino quando genitore viene caricato dal database.

Esempio: Se si dispone di una tabella? DIPENDENTE mappato all'oggetto Employee e contiene un set di oggetti Address. Parent Classe: classe Employee, Bambino classe: Indirizzo Classe

public class Employee { 
private Set address = new HashSet(); // contains set of child Address objects 
public Set getAddress() { 
return address; 
} 
public void setAddresss(Set address) { 
this. address = address; 
} 
} 

Nel Employee.hbm.xml file di

<set name="address" inverse="true" cascade="delete" lazy="false"> 
<key column="a_id" /> 
<one-to-many class="beans Address"/> 
</set> 

Nella configurazione sopra. Se lazy="false": - quando si carica l'oggetto Impiegato che viene caricato anche l'indirizzo dell'oggetto figlio tempo e impostato sul metodo setAddresss(). Se si chiama employee.getAdress(), quindi vengono caricati i dati restituiti. Nuova chiamata al database.

Se lazy="true": - Questa è la configurazione predefinita. Se non si parla di ibernazione, si consideri lazy = true. quando si carica l'oggetto Impiegato che l'indirizzo dell'oggetto figlio tempo non viene caricato. Avete bisogno di una chiamata extra alla base dati per ottenere gli oggetti dell'indirizzo. Se si chiama employee.getAdress(), la query del database del tempo si attiva e restituisce i risultati. Chiamata di database fresca.

+0

Dipendente e Indirizzo non ha relazione Genitore-figlio in questo scenario. È ** relazione 'ha-a' **! – Ram

1

L'inizializzazione pigra è un'ottimizzazione delle prestazioni. Viene utilizzato quando i dati vengono considerati "costosi" per qualche motivo. Ad esempio: se il valore hashCode per un oggetto potrebbe non essere effettivamente necessario dal proprio chiamante, il calcolo del codice hash per tutte le istanze dell'oggetto può essere ritenuto inutile. poiché l'accesso a un file system o rete è relativamente lento, tali operazioni dovrebbero essere rimandate fino a quando non sono assolutamente necessarie.

inizializzazione differita ha due obiettivi: ritardo un'operazione costosa fino a quando è assolutamente necessario vendite il risultato di tale operazione costosa, in modo tale che non sarà necessario ripetere nuovamente

5

In parole semplici, è come te stai facendo una torta e avrai bisogno di 5-10 ingredienti dal frigo. Hai due opzioni: prendi tutti gli ingredienti dal frigo e mettilo sulla tua piattaforma della cucina o porta l'oggetto desiderato quando ti serve .. Allo stesso modo nel caricamento avido recuperi tutte le informazioni su bean e le relative classi (non child o is-a relation ma ha una relazione, cioè la torta ha farina, ha latte, ha panna, ecc. e in caso di caricamento pigro prima porti solo il suo identificatore e i valori che provengono dallo stesso tavolo (ingredienti necessari che prima ti serviranno nella tua ciotola in caso di torta) .. tutte le informazioni che provengono da altre tabelle verranno recuperate come e quando richiesto/utilizzato.

Spero che questo aiuti :)

0

pigro di carico permette di rinviare il recupero associazione o di avere un migliore controllo della strategia di recupero.

Quando si utilizza il caricamento EAGER, si definisce un piano di fetch globale che non può essere sovrascritto al momento della query, il che significa che si è limitati a una decisione presa durante la progettazione del proprio modello di entità. Il EAGER fetching is a code smell, perché la strategia di recupero è una politica di query-time e potrebbe differire da un caso di utilizzo aziendale a un altro.

Il fetching strategy è un aspetto molto importante, in quanto il recupero eccessivo di EAGER può causare seri problemi relativi alle prestazioni.

0

Beh, significa semplicemente caricare i dati di cui hai bisogno al momento invece di caricare interi gruppi di dati contemporaneamente che non utilizzerai ora. In tal modo il tempo di caricamento dell'applicazione è più veloce del solito.

0

Sorprendentemente, nessuna delle risposte parla di come si ottiene in ibernazione dietro gli schermi.

Lazy loading è un modello di progettazione che viene effettivamente utilizzata in sospensione per motivi di prestazioni che comporta tecniche seguenti.


1. codice Byte strumentazione:

migliora la definizione della classe base con sospensione hooks per intercettare tutte le chiamate a tale oggetto entità.

fatto sia in fase di compilazione o eseguire [carico] tempo

1.1 momento della compilazione

  • Messaggio compilazione operazione volta

  • per lo più da Maven/plugins formica

1.2 Durata

  • Se nessun strumentazione fase di compilazione è fatto, questo viene creato in fase di esecuzione Uso delle librerie come javassist

2. Proxies

L'oggetto entità che Hibernate rendimenti sono delega del tipo reale.

Consulta anche: Javassist. What is the main idea and where real use?

Problemi correlati