2016-11-25 41 views
0

我試圖用OpenMP加速執行以下代碼。該代碼用於計算mandelbrot並將其輸出到畫布。使用OpenMP的代碼執行速度較慢

該代碼工作正常,單線程,但我想使用OpenMP,使其更快。我嘗試了各種私有和共享變量的組合,但似乎沒有任何工作到目前爲止。與沒有OpenMP相比,代碼總是運行得慢一點(50000次迭代 - 慢了2秒)。

我使用Ubuntu 16.04並使用GCC進行編譯。

void calculate_mandelbrot(GLubyte *canvas, GLubyte *color_buffer, uint32_t w, uint32_t h, mandelbrot_f x0, mandelbrot_f x1, mandelbrot_f y0, mandelbrot_f y1, uint32_t max_iter) { 
mandelbrot_f dx = (x1 - x0)/w; 
mandelbrot_f dy = (y1 - y0)/h; 
uint16_t esc_time; 
int i, j; 
mandelbrot_f x, y; 

//timer start 
clock_t begin = clock(); 

#pragma omp parallel for private(i,j,x,y, esc_time) shared(canvas, color_buffer) 
for(i = 0; i < w; ++i) { 
    x = x0 + i * dx; 
    for(j = 0; j < h; ++j) { 
     y = y1 - j * dy; 
     esc_time = escape_time(x, y, max_iter); 

     canvas[ GET_R(i, j, w) ] = color_buffer[esc_time * 3]; 
     canvas[ GET_G(i, j, w) ] = color_buffer[esc_time * 3 + 1]; 
     canvas[ GET_B(i, j, w) ] = color_buffer[esc_time * 3 + 2]; 

     } 
} 

//time calculation 
clock_t end = clock(); 
double time_spent = (double)(end - begin)/CLOCKS_PER_SEC; 
printf("%f\n",time_spent); 
} 
該代碼使用

escape_time功能:

inline uint16_t escape_time(mandelbrot_f x0, mandelbrot_f y0, uint32_t max_iter) { 
mandelbrot_f x = 0.0; 
mandelbrot_f y = 0.0; 
mandelbrot_f xtemp; 
uint16_t iteration = 0; 
while((x*x + y*y < 4) && (iteration < max_iter)) { 
    xtemp = x*x - y*y + x0; 
    y = 2*x*y + y0; 
    x = xtemp; 
    iteration++; 
} 
return iteration; 

}

的代碼是從這個倉庫https://github.com/hortont424/mandelbrot

+5

[OpenMP時間和時鐘()的可能重複計算兩個不同的結果](http://stackoverflow.com/questions/10673732/openmp-time-and-clock-calculates-two-different-results) –

回答

1

首先,像暗示的註釋,使用omp_get_wtime()代替clock() (它會給你所有線程累計的時鐘滴答數)來衡量時間。其次,如果我沒有記錯,該算法具有負載平衡的問題,所以儘量使用動態調度:

//timer start 
double begin = omp_get_wtime(); 

#pragma omg parallel for private(j,x,y, esc_time) schedule(dynamic, 1) 
for(i = 0; i < w; ++i) { 
    x = x0 + i * dx; 
    for(j = 0; j < h; ++j) { 
     y = y1 - j * dy; 
     esc_time = escape_time(x, y, max_iter); 

     canvas[ GET_R(i, j, w) ] = color_buffer[esc_time * 3]; 
     canvas[ GET_G(i, j, w) ] = color_buffer[esc_time * 3 + 1]; 
     canvas[ GET_B(i, j, w) ] = color_buffer[esc_time * 3 + 2]; 

     } 
} 

//time calculation 
double end = omp_get_wtime(); 
double time_spent = (double)(end - begin)/CLOCKS_PER_SEC; 
printf("%f\n",time_spent); 
+0

什麼是這個問題的問題?它連續三次讓人投票給我,而沒有說什麼。 – dreamcrash

+0

我認爲這可能來自給出重複標誌的其他人,或者是看到它並認爲其他用戶不值得獲得代表重複問題答案的人的人。這是一個很好的答案,這裏比鏈接的問題更加全面和具體。這裏有一個+1補償。 –

+0

最有可能的,謝謝你的支持 – dreamcrash

0

至於有人提出我的問題是使用時鐘()函數,是衡量CPU的時間造成的。 使用omp_get_wtime()代替解決了我的問題。

+0

你可以用動態測試並告訴我它是否能改善你的表現嗎?,我很想知道,謝謝。 – dreamcrash

+0

我做過了,這是一個學校作業,所以我也測試了這個選項。沒有真正有所作爲。 – martin49