Skip navigation

Hisztogram CPU-n

Hisztogram számítás

A hisztogram száímtá nem egy bonyolult feladat. Képek hisztogramja esetén gyakorlatilag meg kell számolni, hogy a képen adott színű pixelekből hány darab van.

A hisztogram párhuzamos száímtása viszont versenyhelyezeteket teremthet, ezért érdekes ebben a témakörben.

Mielőtt viszont megnéznénk, hogy hogyan is kell hisztogrmot számítáani a GPU-n végezzük el ugyanezt a műveletet a CPU-n.

A program teljes kódja Elérhető itt, vagy a lap alján megtalálható.

Számítás menete

A zámítás megvalósításánál az egyszerűség kedévéért leszögezzük, hogy csak szürkeárnyalaots képek kisztogramját számítjuk ki. A képeknél feltesszük továbbá, hogy az intenzitások 0, és 255 között iegész értékek.

A számításhoz tehát két folog kell.

Először is le kell foglalni, és kinullázni egy tömböt, amiben annyi elem van, ahány intenzitás a képeken.

    unsigned int histo[256];
    for (int i=0; i<256; i++)
        histo[i] = 0;

Majd végig kell mennünk a képpontokon, és az adott képpontok intenzitásához tartozó számlálót növelnünk kell.

    for (int i=0; i<SIZE; i++)
        histo[buffer[i]]++;

És már gyakorlatilag kész is vagyunk. A program többi része csak a keretet adja, részletesebben nem térünk rá ki.

Teljes kód egyben

/* This software contains source code provided by NVIDIA Corporation.
 * The program is based on the example code hist_cpu.cu of Chapter 9
 * of the "CUDA by Example" book.
 * 
 * A program az NVIDIA Corporation által készített programkódot tartalmaz.
 * A program a "Cuda by Example" tankönyv 9. fejezetének hist_cpu.cu 
 * példaprogramjára épül.
 */

#include <ctime>
#include <cstdlib>
#include <iostream>

using namespace std;

#define SIZE    (100*1024*1024)

void* big_random_block( int size ) {
    unsigned char *data = (unsigned char*)malloc( size );
    for (int i=0; i<size; i++)
        data[i] = rand() % 256;

    return data;
}

int main( void ) {
    unsigned char *buffer =
        (unsigned char*)big_random_block( SIZE );

    // capture the start time
    clock_t         start, stop;
    start = clock();

    unsigned int    histo[256];
    for (int i=0; i<256; i++)
        histo[i] = 0;

    for (int i=0; i<SIZE; i++)
        histo[buffer[i]]++;

    stop = clock();
    float   elapsedTime = (float)(stop - start);

    long histoCount = 0;
    for (int i=0; i<256; i++) {
        histoCount += histo[i];
        cout << i << ": " << histo[i] << endl;
    }

    cout << endl;
    cout << "Time to generate:  " << elapsedTime << " msec." << endl;
    cout << "Histogram Sum: " << histoCount << endl;

    free( buffer );
    return 0;
}

Feladatok

  • Írjuk át a kódot, hogy valóban szürkeárnyalatos képekre működjön!