2014-10-22 2 views
0

배열의 초기 크기를 미리 결정할 수 없으므로 realloc을 사용하여 1D 배열의 메모리를 동적으로 조정하는 기능이 있습니다.이 코드를 여러 스레드로 나누어 병렬 처리하려면 thread는 더 작은 1D 배열에서 작동하여 필요한 메모리에 따라 동적으로 다시 조정합니다. 프로세스의 일부로 각 스레드는 작은 배열의 최종 크기를 포함하는 개인 변수도 생성합니다.동적으로 다시 조정할 수있는 배열 및 OpenMP

Openmp에서 (마스터 스레드를 통해)이 배열의 개인 복사본에 액세스하고 각 스레드별로 계산 된 배열의 크기를 기반으로 최종 배열을 얻기 위해 모든 작은 배열을 함께 넣고 싶습니다.

가능합니까 ??

+1

: 왜 불가능합니까? –

+0

예/아니오 답변을 원하십니까? – Nard

+0

나는 그것을하기 위해 최선을 다했지만 어떻게 든 잘되지 않습니다. 나는 예 또는 아니오 대답을 요구하지 않습니다. 나는 그것을 작동시키기 위해 어떤 pragma를 사용해야하는지 묻는다. –

답변

1

std::vector과 같은 동적 배열로 수행 할 수 있습니다. 예를 들어 0과 1 사이의 값을 가진 data이라는 배열과 n 요소가 있고 0.5보다 큰 값을 선택하고 새로운 배열 vec에 저장하려고한다고 가정 해 보겠습니다. 당신이 원하는 것을 정확히 할 수 있습니다.

double data[n]; 
for(int i=0; i<n; i++) data[i] = 1.0*rand()/RAND_MAX; 

std::vector<double> vec; 
#pragma omp parallel 
{ 
    std::vector<double> vec_private; 
    #pragma omp for nowait 
    for(int i=0; i<n; i++) { 
     if(data[i]>0.5) vec_private.push_back(data[i]); 
    } 
    #pragma omp critcal 
    vec.insert(vec.end(), vec_private.begin(), vec_private.end()); 
} 

비판적인 섹션없이 이것을하려면 더 많은 작업이 필요합니다. 그것은 각 배열에 대한 크기의 배열을 저장하고 단일 섹션에서 해당 배열에 대해 누적 합계 (일명 접두어 합계)를 수행해야합니다. 누적 합계를 얻으면 배열을 병행하여 병합 할 수 있습니다.

int *sizea; 
#pragma omp parallel 
{ 
    int nthreads = omp_get_num_threads(); 
    #pragma omp single 
    { 
     sizea = new int [nthreads+1]; 
     sizea[0] = 0; 
    } 
    std::vector<double> vec_private; 
    #pragma omp for schedule(static) nowait 
    for(int i=0; i<n; i++) { 
     if(data[i]>0.5) vec_private.push_back(data[i]); 
    } 
    sizea[omp_get_thread_num()+1] = vec_private.size(); 
    #pragma omp barrier 
    #pragma omp single 
    { 
     int size = 0; 
     for(int i=0; i<nthreads+1; i++) { 
      size += sizea[i]; 
      sizea[i] = size;    
     } 
     vec.resize(size); 
    } 
    std::copy(vec_private.begin(), vec_private.end(), vec.begin()+sizea[omp_get_thread_num()]); 
} 
delete[] sizea;