C'è un modo per vedere quante operazioni costa una funzione, un blocco di codice o una dichiarazione?

0

Supponiamo di avere un telefono in grado di elaborare 1 milione di operazioni al secondo e un microcontrollore in grado di eseguire 1000.

C'è un modo per dire quante operazioni eseguite da una funzione o un blocco di codice è in esecuzione?

Ho una funzione e posso scriverla in modi diversi, un esempio non importa perché sto parlando di tutto il codice che potrei scrivere andando avanti in futuro. Mi piacerebbe sapere quante operazioni si stanno verificando per un blocco specifico. È possibile?

Se è importante, ci sono casi in cui posso scrivere codice in vari modi e ottenere lo stesso risultato:

for (var i:int;i<number;i++) {
    // result
}

for (var property in object) {
    // result is same as previous 
}

for each (var value in object) {
    // result is same as previous
}

Ancora una volta, il codice che ho scritto sopra non ha importanza perché non si tratta di quel codice!

Voglio sapere se c'è un modo per misurare ciò che ogni istruzione, blocco di codice o funzione costa in termini di operazioni.

Spero che forse ci sia un programma che fa parte del sistema operativo o che viene fornito con CPU Intel o AMD che posso eseguire quando eseguo il mio programma che, quando premo un pulsante, mi dirà quante operazioni erano appena stati eseguiti sulla CPU.

Risposta alla domanda duplicata:
La mia domanda è diversa dalla domanda di profilazione. Quando una CPU, GPU o APU (?) Dice che fa 1,4 teraflops e la mia applicazione può funzionare su quel o un microcontrollore che può eseguire 1000 flop voglio sapere se esiste un software che mi dice le operazioni (non il profilo il tempo prende per funzionare) su una dichiarazione, o un blocco di codice. In particolare, perché posso scrivere lo stesso codice in più modi, quindi conoscere queste informazioni è prezioso per me.

    
posta 1.21 gigawatts 22.12.2016 - 22:12
fonte

4 risposte

7

Puoi mettere un limite al numero di cicli della CPU che una determinata istruzione prende guardando il manuale per la specifica CPU che ti interessa. Intel pubblica manuali di istruzioni per ogni singola CPU. Tuttavia, questo ovviamente funziona solo con istruzioni che la CPU comprende, cioè (nel caso di dire un Core i7) codice macchina AMD64. Agner Fog dell'Università Tecnica della Danimarca mantiene un insieme di risorse sull'ottimizzazione del software , incluso un table dei costi di istruzione per le famose CPU AMD64 .

La CPU non capisce, per esempio, C. Pertanto, devi usare qualche programma per interpretare il codice C o tradurre il codice C in codice macchina AMD64. In questo caso, dipende molto più da come il programma implementa questa traduzione / interpretazione rispetto alla CPU.

Oppure, per dirla in breve: no, non c'è modo di dire solo guardando al codice di alto livello quanti cicli della CPU ci vorranno fare. Devi almeno sapere esattamente come sarà tradotto in codice macchina (es. Devi sapere che cosa verrà usato il compilatore, quale versione e cosa comandi esatti della riga di comando) e il tipo esatto , la versione e la revisione della CPU su cui verrà eseguito il codice.

Tuttavia, anche questo ti dirà solo quanti cicli ogni singola istruzione prende. Grazie alla complessa programmazione, superscalarity, pipelining, previsione dei rami e molte altre cose, la CPU può impiegare più o meno cicli per l'intero programma rispetto alla semplice somma dei singoli cicli di istruzioni. Quindi, devi considerare l'interleaving e l'interazione tra le istruzioni.

Oh, e naturalmente, non appena il tuo programma accede alla memoria, il disco o il cielo non consentono la rete, tutte le scommesse sono comunque disattivate.

So che intendevi solo i frammenti di codice come esempi, ma voglio comunque affrontarli: per i tre frammenti di codice che hai postato, suppongo che qualsiasi compilatore ottimizzante degno di questo nome genererebbe lo stesso codice macchina per tutti e tre i loro.

In realtà i cicli di conteggio sono possibili solo su CPU molto semplici, come microcontrollori di piccole dimensioni o CPU datate degli anni '60 e '70. Le moderne CPU ad alte prestazioni generiche fanno così tante ottimizzazioni dietro le quinte e hanno così tante euristiche che è praticamente impossibile.

    
risposta data 22.12.2016 - 22:29
fonte
4

In genere, ignoriamo le specifiche di "quante operazioni" e quali: perché? Perché non importa. Diverse operazioni probabilmente richiedono tempi diversi e quel tempo è specifico per l'implementazione.

Al contrario, utilizziamo i Profiler - praticamente ogni lingua in cui lavori li ha, e ti diranno soprattutto quanto tempo è stato speso in una funzione o in un pezzo di codice. La tempistica è la parte più importante, dal momento che ti dirà dove si trovano gli hang-up nel codice (anche se potresti aver bisogno di compensare manualmente se per esempio chiede l'input dell'utente).

    
risposta data 22.12.2016 - 22:31
fonte
0

Sono abbastanza sicuro che tu abbia un obiettivo che non stai citando perché pensi che sia ovvio. Ma ci sono altri modi per realizzarlo.

Sono abbastanza sicuro che non cerchi massimizzare il numero di cicli.
Scommetto che vuoi ridurli a icona - scopri quali cicli dovresti eliminare. Esistono metodi diversi dal conteggio o dalla profilazione.

Uno è solo un passo unico del codice. Vedrai rapidamente come viene sprecato il tempo.

Un altro è questo metodo . (Alcuni dicono che è solo un altro metodo di profilazione, ma nessun profiler ti dice cosa fa.)

    
risposta data 23.12.2016 - 15:31
fonte
0

Molto, molto più importante del tempo impiegato per ogni affermazione è il tempo necessario per completare il problema e come cresce man mano che il problema si allarga:

link

I tuoi esempi hanno tutti lo stesso ordine: O (n); le differenze tra loro sono probabilmente solo un valore costante. A seconda di cosa sta accadendo all'interno del ciclo (è una ricerca? Somma dei valori?), Potresti essere in grado di applicare un algoritmo più efficiente per ottenere prestazioni migliori.

    
risposta data 03.01.2017 - 23:07
fonte