DELETEALL/MODIFYALL: più veloci o no?

Buon giorno a tutti! Su un Database Navision SQL versione 4.01 sto ottimizzando alcune parti di codice. Utilizzando il Client Monitor per controllare i tempi delle diverse elaborazioni, ho notato che i rallentamenti più evidenti sono causati dalla funzione DELETEALL e MODIFYALL anche se non viene eseguito il codice nei trigger…Ma non dovrebbero essere in realtà più veloci rispetto alla DELETE o MODIFY all’interno di un ciclo? Ci sono delle eccezioni o dei criteri da rispettare per ottenere una prestazione ottimale? Nei diversi incontri in cui si presentava la Versione 4.01 di Navision mi riscordo che uno dei suggerimenti per ottimizzare le prestazioni era proprio quello di utilizzare DELETEALL e MODIFYALL ove possibile… Resto in attesa di ogni vostro commento per capire in cosa sto sbagliando e vi ringrazio anticipatamente. Buon lavoro!

quote:

Buon giorno a tutti! Su un Database Navision SQL versione 4.01 sto ottimizzando alcune parti di codice. Utilizzando il Client Monitor per controllare i tempi delle diverse elaborazioni, ho notato che i rallentamenti più evidenti sono causati dalla funzione DELETEALL e MODIFYALL anche se non viene eseguito il codice nei trigger…Ma non dovrebbero essere in realtà più veloci rispetto alla DELETE o MODIFY all’interno di un ciclo? Ci sono delle eccezioni o dei criteri da rispettare per ottenere una prestazione ottimale? Nei diversi incontri in cui si presentava la Versione 4.01 di Navision mi riscordo che uno dei suggerimenti per ottimizzare le prestazioni era proprio quello di utilizzare DELETEALL e MODIFYALL ove possibile…

ModifyAll e DaleteAll senza l’esecuzione del trigger sono senz’altro più veloci della singola operazione dentro un ciclo questo perchè dentro un ciclo il record è costretto a viaggiare dal server al client mentre l’istruzione modifyall e deleteall può essere eseguita direttamente dal server senza impegno del client. Come mia ottimizzazione nello scrivere del vodice, se devo cancellare un elemento di cui conosco la chiave primaria, non ne faccio la get. Ad esempio: TableItem.“No” := 1000; TableItem.DELETE; Certo è diverso se la selezione è fatta dal mark (che è gestito dal dataset sul client) o se sono presenti indici sift mantenuti da SQL che comunque devono essere aggiornati con conseguente carico e rallentamento della procedura. Anche la presenza di numerose chiavi certo non aiutano le prestazioni. In ogni caso penso che per il client SQL sia più semplice da ottimizzare una chiamata Modifyall/DeleteAll che un un ciclo con findfirst findnext. Ma il mantenimento degli indici sift di SQL viene fatto da una stored procedure o dal client?? Questo però è il mio parere e rimango in ascolto per conferme o smentite! Mi piace imparare :smiley: Matteo

quote:

Anche la presenza di numerose chiavi certo non aiutano le prestazioni. In ogni caso penso che per il client SQL sia più semplice da ottimizzare una chiamata Modifyall/DeleteAll che una un ciclo con findfirst findnext. Questo però è il mio parere e rimango in ascolto per conferme o smentite! Mi piace imparare :smiley:

Questo è anche il mio parere. Ma per il performance, è più facile NON mantenere le chiavi/SIFT su SQL che non servono. O dare un altra chiave da mantenere. Esempio : dai ± 15 chiavi nella tabella 32, io mantengo solo un 1: la chiave primaria. Del resto ho creato 3 nuovi chiavi (con solo alcuni campi, non tanti) e con pochi SIFT-fields.

quote:

quote:
Anche la presenza di numerose chiavi certo non aiutano le prestazioni. In ogni caso penso che per il client SQL sia più semplice da ottimizzare una chiamata Modifyall/DeleteAll che una un ciclo con findfirst findnext. Questo però è il mio parere e rimango in ascolto per conferme o smentite! Mi piace imparare :smiley:

Questo è anche il mio parere. Ma per il performance, è più facile NON mantenere le chiavi/SIFT su SQL che non servono. O dare un altra chiave da mantenere. Esempio : dai ± 15 chiavi nella tabella 32, io mantengo solo un 1: la chiave primaria. Del resto ho creato 3 nuovi chiavi (con solo alcuni campi, non tanti) e con pochi SIFT-fields.
Originally posted by kriki - 2006 Mar 10 : 09:26:13

Drastica come soluzione :slight_smile: … sei soddisfatto delle prestazioni? Sempre ragionando sul funzionamento di SQL percui una chiave molto selettiva da risultati, in termini di tempi di risposta, migliori di un indice SIFT navision (soprattutto guardando nel complesso il costo di mantenimento in scrittura/benefici in lettura), preferisco creare chiavi mirate al massimo evitando i SIFT. Spesso mi trovo a pensare che, a meno di casi eccezionali, l’idea dei SIFT su SQL sia un errore progettuale per evitare di dover riscrivere Navision. Ma se faccio una chiave ottimale con 3 campi e un SIFT mantenuto completamente e in una elaborazione filtro per quei 3 campi e un quarto non in chiave chiedendo CALCSUMS… Navision è costretto a guardarsi la tabella??? Per me sì… Matteo

quote:

Ma se faccio una chiave ottimale con 3 campi e un SIFT mantenuto completamente e in una elaborazione filtro per quei 3 campi e un quarto non in chiave chiedendo CALCSUMS… Navision è costretto a guardarsi la tabella??? Per me sì…

Sì! Tante volte è meglio non mantenere SIFT su SQL. Questo perché SQL è molto bravo a fare delle somme con tanti records. Alcune migliaia di records non è un problema per SQL.

ciao. vi descrivo la mia esperienza. tabella con 9 milioni di record (circa 100 campi per record). 1 chiave con di 5 campi con 3 campi sift. chiave= campo1 campo2 campo3 campo4 campo5 sift (maintain = NO) somma1 somma2 somma3 nav 4, sql2000. analizzando il problema abbiamo riscontrato che il buon DBMS a volte decideva che per calcolare i sift piuttsto che utilizzare la chiave appositamente creata a suo parere era megloi scorrere i dati per chiave primaria… cioè un’ora di elaborazione…piantando il server perchè i calcsums sono operaizoni server con alta priorità… Soluzione? prendere in giro il DBMS: ho cambiato la chiave in questo modo: chiave= campo1 campo2 campo3 campo4 campo5 somma1 somma2 somma3 sift (maintain = NO) somma1 somma2 somma3 tempo di esecuzione = 30 secondi senza bloccare la macchina… ultima considerazione. nei changedoc degli ultimi sp di navision c’è sempre un riferimento del tipo “…abbiamo migliorato la gestione dei SIFT…” cosa significhi non lo so… Qeusto week-end installo l’SP1 da questo cliente e verifico se conta qualcosa… ciao a tutti

quote:

Soluzione? prendere in giro il DBMS: ho cambiato la chiave in questo modo: chiave= campo1 campo2 campo3 campo4 campo5 somma1 somma2 somma3 sift (maintain = NO) somma1 somma2 somma3

Ciao. Quindi hai messo nella chiave i stessi decimal utilizzati per le somme? Non è che la migliore velocità di risposta sia dovuta al fatto che SQL non ha bisogno di leggere le pagine di dati della tabella ma gli basta leggere la stessa chiave che sta scansionando? E come frammentazione della chiave/tabella (causato dal modificarsi dei decimal), sei soddisfatto? O sono dati storici i cui decimal vengono aggiornati di rado e quindi tutto sommato non è un problema? Ho un cliente su SQL che lamenta che quando a fine giornata una quarantina di user, divisi su 12 società nello stesso database fanno pesantemente tutti assieme la spedizione degli ordini e spesso anche la fattura accompagnatoria, “appare la clessidra”. Mi sto riguardando le procedure (senza comunque stravolgere i posting)ottimizzandole un po’come codice e verificando l’effettiva necessità di enormi chiavi+sift dello standard, contro la creazioni di chiavi molto selettive e corte calibrate… quando finisco i test magari faccio sapere i risultati :slight_smile: Grazie per il tuo post… mi sta dando tanto su cui ragionare :)) Matteo

In Navision è possibile forzare quale indice il SQL Server Query Optimizer deve usare tramite l’Index Hinting. La procedura è descritta nel captiolo 12 del Manuale Install and Configuration pag 406. In ogni caso conviene assicurarsi che le statistiche siano aggiornate perchè gli indici sono scleti dal SQL Server Query Optimizer sulla base di queste.

Ne approfitto per chiedere un’altra informazione: nella versione 2.60 di Navision, i flowfields non visualizzati in maschera non vengono calcolati mentre nella versione 4.01 mi sono accorta che tali campi anche se non inseriti vongono comunque calcolati rallentando notevolmente il tempo di visualizzazione dei dati. Esiste un modo per non calcolare i flowfileds non presenti nella maschera? Grazie a tutti!