|
|||||||
|
|
|
![]() |
|
|
Strumenti |
|
|
#1 |
|
Senior Member
Iscritto dal: Nov 2002
Messaggi: 6424
|
[C] Ottimizzazione spinta
Ciao ragazzi,
avrei bisogno di ultraottimizzare questo spezzone di codice: Codice:
register float32 * punt;
register float32 sample_r,sample_i;
punt = &trdiff[4*i_idx1];
for(m = 0; m < *ntot; m++)
for( k = 0; k < i_idx2-i_idx1+1 ; k++) {
sample_r = *punt + up_interp* *(punt+1);
sample_i = *(punt + 2) +up_interp* *(punt + 3);
punt +=4;
numm[ m][k].r += sample_r;
numm[ m][k].i += sample_i;
denom[m] += sample_r * sample_r + sample_i * sample_i;
}
Grazie Ultima modifica di Unrue : 29-06-2009 alle 22:14. |
|
|
|
|
|
#2 |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
Secondo me oltre un certo punto ogni ottimizzazione "sintattica" apporta vantaggi trascurabili... ad un certo punto bisogna considerare l'ottimizzazione "semantica". Ad esempio il tuo codice ha complessità O(N*M) dove:
N = max(*ntot) M = max(i_idx2-i_idx1+1) Puoi fare di meglio? P.S.: Se vuoi ottimizzare (sintatticamente) al max devi avere una grande conoscenza del compilatore. Non so quale usi, ma cmq non sono espertissimo in questo campo. Prova a studiare le tecniche di ottimizzazione che usa il tuo compilatore e cerca di scrivere il codice che le sfrutti al meglio. Ma il gioco non vale la candela... almeno per la maggior parte delle applicazioni che riesco ad immaginare! |
|
|
|
|
|
#3 |
|
Senior Member
Iscritto dal: Nov 2002
Messaggi: 6424
|
Ciao,
grazie per la risposta. Dunque, sto utilizzando il compilatore Intel. Diciamo che questa applicazione non dove girare su molte macchine ma più o meno sempre sulla stessa ( AMD Opteron) Riguardo il tuo consiglio, purtroppo non posso eliminare il doppio ciclo. |
|
|
|
|
|
#4 |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
Eh... su quello non avevo dubbi!
|
|
|
|
|
|
#5 |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
Ma forse ho esagerato troppo...
|
|
|
|
|
|
#6 |
|
Senior Member
Iscritto dal: Jul 2002
Città: Reggio Calabria -> London
Messaggi: 12112
|
se hai + di un core a disposizione sulla tua macchina puoi usare i thread, altrimenti credo che la cosa migliore sarebbe ottimizzare l'algoritmo come ha già detto ikon'cluster....
cmq è una matrice completa? o magari è sparsa o diagonale? Negli ultimi due casi dovresti poter guadagnare molto a livello algoritmico.....
__________________
|
|
|
|
|
|
#7 |
|
Senior Member
Iscritto dal: Feb 2006
Messaggi: 1304
|
Dato che lo stride di punt è 4 elementi, dovrebbe essere possibile usare le SIMD... forse
Oppure potresti spezzare il for interno su tutti i cores con threads che lo eseguirebbero più o meno parallelamente. L'unica ottimizzazione che mi viene in mente in quel codice è salvarsi i_idx2-i_idx1+1 invece che ricalcolarlo N*M volte... ed anche usare ++k e ++m invece che k++ e m++... dovrebbe risparmiare un paio di istruzioni asm.
|
|
|
|
|
|
#8 |
|
Senior Member
Iscritto dal: Oct 2007
Città: Padova
Messaggi: 4131
|
[OT]Il preincremento è più "economico" del postincremento in termini di assembly? Nel senso, lo è sempre? Non conosco niente di assembly...[/OT]
__________________
As long as you are basically literate in programming, you should be able to express any logical relationship you understand. If you don’t understand a logical relationship, you can use the attempt to program it as a means to learn about it. (Chris Crawford) |
|
|
|
|
|
#9 |
|
Senior Member
Iscritto dal: Jul 2002
Città: Reggio Calabria -> London
Messaggi: 12112
|
con i compilatori moderni utilizzare a++ o ++a dovrebbe essere la stessa cosa.
Anche il fatto di salvarsi la sottrazione in una variabile locale *dovrebbe* essere già fatto dal compilatore...
__________________
|
|
|
|
|
|
#10 | |
|
Senior Member
Iscritto dal: Feb 2006
Messaggi: 1304
|
Quote:
quindi si dovrebbe risparmiare una creazione ed un'assegnazione. Ma non so niente di assembly Cmq io lo uso sempre perchè non costa niente, se funziona meglio ![]() In ogni caso il compilatore *dovrebbe* farle da solo ste cose, ma dato che qua si parla di ottimizzazione massima il *dovrebbe* non è ammesso... Ultima modifica di Tommo : 30-06-2009 alle 14:17. |
|
|
|
|
|
|
#11 | |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
Quote:
|
|
|
|
|
|
|
#12 |
|
Senior Member
Iscritto dal: Nov 2002
Messaggi: 6424
|
|
|
|
|
|
|
#13 |
|
Senior Member
Iscritto dal: Nov 2005
Messaggi: 2782
|
Potresti anche salvare il valore di *ntot in una variabile per evitare la dereferenziazione, risparmieresti un accesso alla memoria. Ma temo che tutte le ottimizzazioni che stiamo proponendo siano già attuate dal compilatore...
|
|
|
|
|
|
#14 |
|
Senior Member
Iscritto dal: Apr 2000
Città: Vicino a Montecatini(Pistoia) Moto:Kawasaki Ninja ZX-9R Scudetti: 29
Messaggi: 53971
|
Allora...io proverei così:
sample_r = A + K * B; sample_i = C + K * D; Quindi denom[m] += A^2 + K^2*B^2 + AKB + C^2 + K^2*D^2 + CKB N = i_idx2 - i_idx1 denom[m] = somma per K che va da 0 a N(A^2 + K^2*B^2 + AKB + C^2 + K^2*D^2 + CKB) = NA^2 + NC^2 + (B^2 + D^2)*somma(K^2) + (AB + CD)*somma(K) somma(K) = (N*(N+1))/2 somma(K^2) = N(N+1)(2N+1)/6 Da numm[m][k] ci passi solo una volta, cosa c'è prima dentro la struct ? |
|
|
|
|
|
#15 | |
|
Senior Member
Iscritto dal: Nov 2002
Messaggi: 6424
|
Quote:
Ultima modifica di Unrue : 30-06-2009 alle 16:34. |
|
|
|
|
|
|
#16 |
|
Senior Member
Iscritto dal: Apr 2000
Città: Vicino a Montecatini(Pistoia) Moto:Kawasaki Ninja ZX-9R Scudetti: 29
Messaggi: 53971
|
Aspetta, non avevo visto che punt viene incrementato di 4...cancella tutto quello che ho scritto
|
|
|
|
|
|
#17 |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
|
|
|
|
|
|
#18 |
|
Senior Member
Iscritto dal: Jul 2002
Messaggi: 869
|
Potresti provare a compilare con il gcc insieme all'opzione -O3 e vedere come va l'eseguibile rispetto a quello compilato con l'intel.
Da quello che ho letto in giro il compilatore intel dovrebbe generare codici più performanti a patto di compilare con i flag giusti che sfruttano l'architettura. Fai il confronto tra i due eseguibili e se va meglio quello prodotto dal gcc allora forse devi usare qualche altro flag sul compilatore intel. P.S. Anche se sono poche righe di codice, potresti analizzarle sfruttando il valgrind come profiler e il kcachegrind per vedere ogni istruzione e ogni ciclo quando tempo di cpu impiega (è il modo migliore per trovare i colli di bottiglia).
__________________
Notebook: MBP 15 i7 Retina, (Mid 2014) |
|
|
|
|
|
#19 |
|
Registered User
Iscritto dal: May 2009
Messaggi: 300
|
fracarro x esempio è uno furbo...
|
|
|
|
|
|
#20 |
|
Senior Member
Iscritto dal: Oct 2007
Città: Padova
Messaggi: 4131
|
Magari può interessarti Acovea
__________________
As long as you are basically literate in programming, you should be able to express any logical relationship you understand. If you don’t understand a logical relationship, you can use the attempt to program it as a means to learn about it. (Chris Crawford) |
|
|
|
|
| Strumenti | |
|
|
Tutti gli orari sono GMT +1. Ora sono le: 11:20.





















