Στο gist αυτό θα αναρτηθούν λύσεις και υποδείξεις κατά τη διεξαγωγή του εργαστηρίου.
libtbb2 libtbb-dev libtbb2-dbg libtbb-doc tbb-examples
g++
| // Serial dummy load | |
| // Compile with: g++ -Wall -O2 testload-serial.cpp -o testload-serial | |
| #include <iostream> | |
| #define N 10000000 | |
| #define R 100 | |
| using namespace std; | |
| void testmap(float& a) { | |
| for (size_t j=0;j<R;++j) { | |
| a = a+j; | |
| } | |
| } | |
| // Serial implementation | |
| void ApplyMapSerial(float a[],size_t n) { | |
| for (size_t i=0;i<n;++i) { | |
| testmap(a[i]); | |
| } | |
| } | |
| int main() { | |
| // alloc array | |
| float *a = new float[N]; // will throw exception if alloc error | |
| // init array | |
| for (size_t i=0;i<N;++i) { | |
| a[i] = 3.0; | |
| } | |
| // execute test load | |
| ApplyMapSerial(a,N); | |
| // check results | |
| for (size_t i=0;i<N;++i) { | |
| if (a[i]!=4953.0) { | |
| cout << "error " << a[i] << endl; | |
| break; | |
| } | |
| } | |
| // free array | |
| delete[] a; // NOTE: the syntax of freeing arrays! | |
| return 0; | |
| } |
| // Tests TBB parallel_for with dummy load | |
| // Compile with: g++ -Wall -O2 -std=c++11 testload-tbb.cpp -o testload-tbb -ltbb | |
| #include <iostream> | |
| #include "tbb/tbb.h" | |
| #define N 10000000 | |
| #define R 100 | |
| using namespace std; | |
| void testmap(float& a) { | |
| for (size_t j=0;j<R;++j) { | |
| a = a+j; | |
| } | |
| } | |
| // TBB implementation with lambda function | |
| void ApplyMapTbb(float a[],size_t n) { | |
| tbb::parallel_for(size_t(0),n,[&](size_t i) { // NOTE: Index params (1st,2nd) must be of same type | |
| testmap(a[i]); // that is, "parallel_for(0,n,..." throws compiler error | |
| }); | |
| } | |
| int main() { | |
| // alloc array | |
| float *a = new float[N]; // will throw exception if alloc error | |
| // init array | |
| for (size_t i=0;i<N;++i) { | |
| a[i] = 3.0; | |
| } | |
| // execute test load | |
| ApplyMapTbb(a,N); | |
| // check results | |
| for (size_t i=0;i<N;++i) { | |
| if (a[i]!=4953.0) { | |
| cout << "error " << a[i] << endl; | |
| break; | |
| } | |
| } | |
| // free array | |
| delete[] a; // NOTE: the syntax of freeing arrays! | |
| return 0; | |
| } |
| // Tests TBB parallel_for with dummy load | |
| // Compile with: g++ -Wall -O2 -std=c++11 testload-tbb2.cpp -o testload-tbb2 -ltbb | |
| #include <iostream> | |
| #include "tbb/tbb.h" | |
| #define N 10000000 | |
| #define R 100 | |
| using namespace std; | |
| void testmap(float& a) { | |
| for (size_t j=0;j<R;++j) { | |
| a = a+j; | |
| } | |
| } | |
| // TBB implementation with body as a lambda function, alternative version | |
| void ApplyMapTbb(float a[],size_t n) { | |
| tbb::parallel_for(tbb::blocked_range<size_t>(0,n),[&](const tbb::blocked_range<size_t>& r) { | |
| for (size_t i=r.begin();i!=r.end();++i) { | |
| testmap(a[i]); | |
| } | |
| }); | |
| } | |
| int main() { | |
| // alloc array | |
| float *a = new float[N]; // will throw exception if alloc error | |
| // init array | |
| for (size_t i=0;i<N;++i) { | |
| a[i] = 3.0; | |
| } | |
| // execute test load | |
| ApplyMapTbb(a,N); | |
| // check results | |
| for (size_t i=0;i<N;++i) { | |
| if (a[i]!=4953.0) { | |
| cout << "error " << a[i] << endl; | |
| break; | |
| } | |
| } | |
| // free array | |
| delete[] a; // NOTE: the syntax of freeing arrays! | |
| return 0; | |
| } |
| // Serial triad benchmark | |
| // Compile with: g++ -Wall -O2 triad-serial.cpp -o triad-serial | |
| #include <iostream> | |
| #define N 10000000 | |
| #define R 100 | |
| using namespace std; | |
| // Serial implementation | |
| void ApplyTriadSerial(double a[],double b[], double c[], double d[],size_t n) { | |
| for (size_t i=0;i<n;++i) { | |
| for (size_t j=0;j<R;++j) { | |
| a[i] = b[i]*c[i]+d[i]; | |
| } | |
| } | |
| } | |
| int main() { | |
| // alloc arrays | |
| double *a = new double[N]; | |
| double *b = new double[N]; | |
| double *c = new double[N]; | |
| double *d = new double[N]; | |
| // init arrays | |
| for (size_t i=0;i<N;++i) { | |
| a[i]=2.0*i; | |
| b[i]=-1.0*i; | |
| c[i]=i+5.0; | |
| d[i]=-7.0*i; | |
| } | |
| // execute test load | |
| ApplyTriadSerial(a,b,c,d,N); | |
| // check results | |
| for (size_t i=0;i<N;++i) { | |
| if (a[i]!=(b[i]*c[i]+d[i])) { | |
| cout << "error " << (b[i]*c[i]+d[i]) << ": " << a[i] << endl; | |
| break; | |
| } | |
| } | |
| // free arrays | |
| delete[] a; | |
| delete[] b; | |
| delete[] c; | |
| delete[] d; | |
| return 0; | |
| } |
| // TBB implementation with body as a lambda function | |
| void ApplyTriadTbb(double a[],double b[],double c[],double d[],size_t n) { | |
| tbb::parallel_for(size_t(0),n,[&](size_t i) { | |
| for (size_t j=0;j<R;++j) { | |
| a[i] = b[i]*c[i]+d[i]; | |
| } | |
| }); | |
| } |
| // TBB implementation with body as a lambda function | |
| void ApplyTriadTbb(double a[],double b[],double c[],double d[],size_t n) { | |
| tbb::parallel_for(tbb::blocked_range<size_t>(0,n),[&](const tbb::blocked_range<size_t>& r) { | |
| for (size_t i=r.begin();i!=r.end();++i) { | |
| for (size_t j=0;j<R;++j) { | |
| a[i] = b[i]*c[i]+d[i]; | |
| } | |
| } | |
| }); | |
| } | |