Domanda

La profilazione del mio programma e la funzione print richiedono molto tempo.Come posso inviare l'output di byte "grezzo" direttamente a stdout invece di utilizzare fwrite e renderlo più veloce (è necessario inviare tutti i 9 byte in print() contemporaneamente allo stdout)?

void print(){
    unsigned char temp[9];

    temp[0] = matrix[0][0];
    temp[1] = matrix[0][1];
    temp[2] = matrix[0][2];
    temp[3] = matrix[1][0];
    temp[4] = matrix[1][1];
    temp[5] = matrix[1][2];
    temp[6] = matrix[2][0];
    temp[7] = matrix[2][1];
    temp[8] = matrix[2][2];

    fwrite(temp,1,9,stdout);

}

La matrice è definita globalmente come una matrice di caratteri senza segno[3] [3];

È stato utile?

Soluzione

IO non è un'operazione poco costoso. E ', infatti, un blocco il funzionamento, il che significa che il sistema operativo può prevenire il processo quando si chiama write per consentire a più processi CPU-bound per l'esecuzione, prima che il dispositivo IO che si sta scrivendo per la completa operazione.

La funzione solo il primo ciclo è possibile utilizzare (se si sta sviluppando su una macchina * nix), è quello di utilizzare la funzione write crudo, ma anche in questo caso le prestazioni non sarà così molto più veloce di quanto lo sia ora. In poche parole: IO è costoso.

Altri suggerimenti

La risposta nominale superiore sostiene che IO è lento.

Ecco un rapido punto di riferimento con un numero sufficientemente ampio di buffer di prendere il sistema operativo di fuori del percorso prestazioni critiche, ma solo se si è disposti a ricevere la vostra uscita nelle blurps giganti. Se la latenza al primo byte è il tuo problema, è necessario eseguire in modalità "spizzichi".

Scrivi 10 milioni di dischi da un array di byte nove

Mint 12 AMD64 su 3GHz CoreDuo sotto gcc 4.6.1

   340ms   to /dev/null 
   710ms   to 90MB output file 
 15254ms   to 90MB output file in "dribs" mode 

FreeBSD 9 AMD64 su 2.4GHz CoreDuo sotto clang 3.0

   450ms   to /dev/null 
   550ms   to 90MB output file on ZFS triple mirror
  1150ms   to 90MB output file on FFS system drive
 22154ms   to 90MB output file in "dribs" mode

Non c'è niente lenta in merito a IO se si può permettere di buffer in modo corretto.

#include <stdio.h> 
#include <assert.h> 
#include <stdlib.h>
#include <string.h>

int main (int argc, char* argv[]) 
{
    int dribs = argc > 1 && 0==strcmp (argv[1], "dribs");
    int err;
    int i; 
    enum { BigBuf = 4*1024*1024 };
    char* outbuf = malloc (BigBuf); 
    assert (outbuf != NULL); 
    err = setvbuf (stdout, outbuf, _IOFBF, BigBuf); // full line buffering 
    assert (err == 0);

    enum { ArraySize = 9 };
    char temp[ArraySize]; 
    enum { Count = 10*1000*1000 }; 

    for (i = 0; i < Count; ++i) {
        fwrite (temp, 1, ArraySize, stdout);    
        if (dribs) fflush (stdout); 
    }
    fflush (stdout);  // seems to be needed after setting own buffer
    fclose (stdout);
    if (outbuf) { free (outbuf); outbuf = NULL; }
}

La forma più cruda di uscita si può fare è la probabile la chiamata di sistema write, come questo

write (1, matrix, 9);

1 è il descrittore di file per standard out (0 è standard, e 2 è errore standard). Il vostro fuori standard sarà solo scrivere veloce come quella lettura all'altra estremità (vale a dire il terminale, o il programma che stai pipeing in), che potrebbe essere piuttosto lento.

Non sono sicuro al 100%, ma si potrebbe provare a impostare non-blocking IO su fd 1 (utilizzando fcntl) e sperare che il sistema operativo sarà tampone per voi fino a che non può essere consumato da l'altra estremità. E 'stato un po', ma penso che funziona in questo modo

fcntl (1, F_SETFL, O_NONBLOCK);

YMMV però. Si prega di correggermi se sbaglio sulla sintassi, come ho detto, è stato un po '.

Forse il tuo problema non è che fwrite () è lento, ma che è tamponato. Prova a chiamare fflush (stdout) dopo il fwrite ().

Questo dipende tutti davvero dalla vostra definizione di lento in questo contesto.

Tutto stampa è piuttosto lento, anche se iostreams sono veramente lento per la stampa.

La cosa migliore sarebbe quella di utilizzare printf, qualcosa sulla falsariga di:

printf("%c%c%c%c%c%c%c%c%c\n", matrix[0][0], matrix[0][1], matrix[0][2], matrix[1][0],
  matrix[1][1], matrix[1][2], matrix[2][0], matrix[2][1], matrix[2][2]);

Si può semplicemente:

std::cout << temp;

printf è più C-Style.

Tuttavia, le operazioni di IO sono costosi, in modo da utilizzare con saggezza.

Come tutti hanno sottolineato, l'IO in un circuito interno ristretto è costoso.Normalmente finisco per eseguire il cout condizionale di Matrix in base ad alcuni criteri quando richiesto per eseguirne il debug.

Se la tua app è un'app console, prova a reindirizzarla a un file, sarà molto più veloce rispetto all'aggiornamento della console.ad esempio app.exe > matriceDump.txt

Cosa c'è di sbagliato con:

fwrite(matrix,1,9,stdout);

l'una e le due matrici dimensionali occupano la stessa memoria.

Provare a eseguire il programma di due volte. Una volta con uscita e una volta senza. Si noterà che, nel complesso, l'uno senza l'io è il più veloce. Inoltre, si potrebbe fork del processo (o creare un filo), una scrittura su un file (stdout), e uno a fare le operazioni.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top