openmp quan trọng

Aug 19 2020

Theo câu hỏi này , cho đoạn mã bên dưới ( từ ví dụ về tài liệu MS OpenMP )

// omp_critical.cpp
// compile with: /openmp
#include <omp.h>
#include <stdio.h>
#include <stdlib.h>

#define SIZE 10

int main()
{
    int i;
    int max;
    int a[SIZE];

    for (i = 0; i < SIZE; i++)
    {
        a[i] = rand();
        printf_s("%d\n", a[i]);
    }

    max = a[0];
    #pragma omp parallel for num_threads(4)
    for (i = 1; i < SIZE; i++)
    {
        if (a[i] > max)
        {
            #pragma omp critical
            {
                // compare a[i] and max again because max
                // could have been changed by another thread after
                // the comparison outside the critical section
                if (a[i] > max)
                    max = a[i];
            }
        }
    }

    printf_s("max = %d\n", max);
}

Tôi có thể loại bỏ bên ngoài nếu kiểm tra và làm

max = a[0];
#pragma omp parallel for num_threads(4)
for (i = 1; i < SIZE; i++)
{
    #pragma omp critical
    {
        // compare a[i] and max again because max
        // could have been changed by another thread after
        // the comparison outside the critical section
        if (a[i] > max)
            max = a[i];
    }
}

Trả lời

1 cos_theta Aug 19 2020 at 16:53

Bạn có thể, nhưng điều này dẫn đến việc thực thi tuần tự một cách hiệu quả. Các luồng liên tục chờ đợi để đi vào phần quan trọng sao cho chỉ một luồng thực thi phần thân của vòng lặp tại một thời điểm. Do đó, bạn nhận được cùng một hiệu suất (thậm chí có thể tồi tệ hơn do chi phí đồng bộ hóa) so với một vòng lặp nối tiếp đơn thuần.

Ví dụ từ tài liệu MS chỉ đồng bộ hóa nếu gặp phải giá trị lớn nhất mới. Điều này cho phép xử lý song song tất cả các giá trị thấp hơn cho đến thời điểm này.

Như đã đề xuất trong các nhận xét, hãy sử dụng cấu trúc rút gọn.