基于OpenMP的线程进度追踪问题:无法实现并行执行
问题分析与解决方案
你的程序未实现并行的核心原因是编译时未启用OpenMP支持,同时还有几个细节问题需要修正:
关键问题点
- 未启用OpenMP编译选项:GCC默认不会解析OpenMP指令,必须添加
-fopenmp参数编译,否则#pragma omp parallel sections会被忽略,程序串行执行——先进入print_every_second的死循环(done初始为0),导致increment_to_10_million完全没机会执行。 - 缺少sleep函数的头文件:
sleep函数定义在<unistd.h>中,未包含会引发编译警告或运行异常。 - printf格式错误:原代码中
printf("%d\n!", counter);的换行符位置错误,会导致输出格式混乱,应调整为printf("%d!\n", counter);。 - done变量的同步问题:修改
done时无同步机制,可能导致打印线程无法及时感知到done的变化,建议用#pragma omp atomic确保修改的原子性和内存可见性。
修正后的代码
#include <stdio.h> #include <omp.h> #include <unistd.h> // 引入sleep函数的头文件 volatile int counter = 0; volatile int done = 0; void print_every_second() { while (!done) { #pragma omp critical { printf("%d!\n", counter); // 修正输出格式 } sleep(1); } } void increment_to_10_million() { for (int i = 1; i <= 10000000; ++i) { #pragma omp atomic counter++; } #pragma omp atomic // 确保done的修改被其他线程及时感知 done = 1; } int main() { #pragma omp parallel sections { #pragma omp section { print_every_second(); } #pragma omp section { increment_to_10_million(); } } printf("Both threads have finished.\n"); return 0; }
编译与运行命令
使用GCC编译时必须添加-fopenmp选项以启用OpenMP支持:
gcc -fopenmp progress_tracker.c -o progress_tracker ./progress_tracker
编译运行后,两个线程会并行执行:一个线程每秒打印当前计数器值,另一个线程递增计数器到1000万,完成后设置done为1,打印线程退出循环,最终程序正常结束。
内容的提问来源于stack exchange,提问作者Piece - kun
相关产品推荐
相关产品推荐

