Chiamata di singolo database e iterazione in memoria rispetto a più chiamate al database e più iterazioni minori

1

Sto progettando una nuova applicazione che è molto semplice, ma mi aspetto che cresca e non voglia che debba refactoring lungo la linea. La mia sfida è che in un metodo, o ho bisogno di recuperare migliaia (ad esempio 20.000) di record dal database e iterare attraverso di essi in memoria o, effettuare più chiamate in un ciclo (ad esempio 200 richieste per 100 record ciascuna).

Ho visto questa domanda simile che si appoggia al" meno database chiama, la migliore "linea di pensiero. Esiste un limite massimo al numero di elementi che si dovrebbero / non dovrebbero scorrere in un'applicazione Windows? Questo approccio potrebbe essere soggetto a problemi di memoria che potrebbero annullare i vantaggi in termini di prestazioni?

Questo non è limitato a uno scenario specifico e ho già pensato prima e ho scelto quest'ultima opzione (più richieste per dataset più piccoli).

Sto pensando troppo a questo e dovrei arrivarci?

    
posta Daniel 09.10.2018 - 16:38
fonte

2 risposte

5

"Meno chiamate al database, meglio è" falso dimostrabile. Se questo fosse il caso, la tecnica preferita sarebbe caricare ampie sezioni del database nell'applicazione all'avvio dell'applicazione e fare gran parte dell'elaborazione in memoria, ma la maggior parte delle applicazioni non è progettata in questo modo.

Quindi si tratta di trovare il percorso ottimale. Nella maggior parte dei casi, il modo in cui lo fai è misurare le tue prestazioni. Scopri quale approccio è il più ottimale (in termini di velocità, latenza di rete e utilizzo della memoria), e fallo.

Per il tuo esempio specifico, potresti evitare la maggior parte del traffico di rete e della latenza eseguendo l'elaborazione sul server del database, se questa è un'opzione. Esistono molti scenari in cui è possibile scrivere un'istruzione SQL e ottenere i risultati indietro senza trasferire tutti i record sul filo per l'elaborazione.

    
risposta data 09.10.2018 - 16:49
fonte
1

Generalmente le chiamate sql all'interno di un ciclo sono una delle cose più lente che puoi fare.

È sempre più veloce ottenere prima tutti i dati e poi ricollegarli. L'ovvia limitazione è la memoria disponibile del computer che esegue la tua app.

Questo può essere ottenuto normalmente semplicemente modificando l'SQL in un paio di selezioni più grandi. ad esempio

prima

select from parent where x
foreach parent
    select from child where parentid=y
next

Dopo

select from parent left join child where x
foreach row
    if parentid != last parentId
          new parent
    new child
next

o una variante con due selezioni prima del ciclo che mette tutti i bambini in una hashmap per una rapida ricerca. Che è discutibilmente meglio se stai memorizzando i risultati nella cache.

Vorrei sostenere l'uso di un repository come questo ..

var parents = repo.GetParentsWhereX(x)
var children = repo.GetChildernForParentsWithX(x)
foreach parent....

Che offre la maggior parte delle prestazioni evitando l'oggetto tabella combinata.

Se trovi questo tipo di selezione che restituisce troppi dati con cui lavorare, allora puoi passare a una query paginata. Ma in genere trovo che sia una micro ottimizzazione e la utilizzo solo in presenza di elementi come le esportazioni di dati bulk.

    
risposta data 09.10.2018 - 18:41
fonte

Leggi altre domande sui tag