c - 线程,定期生成 VS。陷入无限临时循环?

标签 c multithreading optimization pthreads

这不是技术问题,而是概念问题。我的程序需要在后台处理多项任务。就我而言,出于以下几个原因,我认为线程比进程更合适:

  • 后台任务并不繁重,但必须定期处理。
  • 所有线程都需要操作一个共享资源。完整的进程需要设置一个共享内存段,这在我的情况下不合适(资源没有固定大小)。当然,此资源受互斥体保护。

我考虑的另一件事是 main() 函数需要能够在需要时结束所有后台任务(这意味着加入线程)。

现在,这里有两个实现:

1 个线程,在内部循环。

void *my_thread_func(void* shared_ressource)
{
    while(1){
        do_the_job();
        sleep(5);
    }
}

// main()
pthread_create(&my_thread, NULL, my_thread_func, (void*)&shared_ressource);
pthread_kill(my_thread, 15); 
// pthread_cancel(my_thread);
pthread_join(my_thread, NULL);

注意:在这种情况下,main() 需要在线程加入之前发出信号(或取消),否则它会挂起。如果线程在终止之前没有时间进行 sem_post,这可能很危险。

n个线程,向外循环。

void *my_thread_func(void* shared_ressource)
{
    do_the_job();
}

// main()
while(1){
    pthread_create(&my_thread, NULL, my_thread_func, (void*)&shared_ressource);
    pthread_join(my_thread, NULL);
    sleep(5);
}

注意:在这种情况下,main() 不会自然地卡在 pthread_join 上,它只需要终止它自己的连续循环(例如使用“ bool 值”)。

现在,我需要一些帮助来比较这两者。线程是轻量级结构,但是生成过程对于第二个实现来说是否过于繁重?还是无限循环在不应该的时候保持线程?目前,我更喜欢第二种实现,因为它保护了信号量:线程在 sem_post 之前不会终止。我关心的是优化,而不是功能。

最佳答案

让你的后台线程不断地产生和死亡往往是低效的。让一定数量的线程保持事件状态通常要好得多,以便在后台工作可用时为其提供服务。

但是,通常最好也避免线程取消。相反,我建议使用条件变量和退出标志:

void *my_thread_func(void *shared_resource)
{
    struct timespec timeout;

    pthread_mutex_lock(&exit_mutex);

    do
    {
        pthread_mutex_unlock(&exit_mutex);
        do_the_job();

        clock_gettime(CLOCK_REALTIME, &timeout);
        timeout.tv_sec += 5;

        pthread_mutex_lock(&exit_mutex);
        if (!exit_flag)
            pthread_cond_timedwait(&exit_cond, &exit_mutex, &timeout);
    } while (!exit_flag)

    pthread_mutex_unlock(&exit_mutex);
}

当主线程想要后台线程退出时,它会设置退出标志并向条件变量发出信号:

pthread_mutex_lock(&exit_mutex);
exit_flag = 1;
pthread_cond_signal(&exit_cond);
pthread_mutex_unlock(&exit_mutex);
pthread_join(my_thread, NULL);

(您实际上应该强烈考虑使用 CLOCK_MONOTONIC 而不是默认的 CLOCK_REALTIME,因为前者不受系统时钟变化的影响。这需要使用 pthread_condattr_setclock()pthread_cond_init() 设置条件变量使用的时钟。)

关于c - 线程,定期生成 VS。陷入无限临时循环?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21801791/

相关文章:

c++ - Win32 函数可以在同一个线程上异步运行吗?

java - 如何在 JFrame 退出时运行终止命令?

c++ - 随机数数组的优化提示

c++ - 编译器会优化静态函数的未使用参数吗?

c - for 循环中 *(&a – i) 的含义。这是乘法吗?

java - 保持 Java 程序无限期运行的有效方法?

haskell - 使用 -hy 进行 GHC 堆分析 - 什么是 *(星号)?

java - 在迭代循环中使用字节是否更有效?

c - 在C中逐行反序列化字符串

android - Android AsyncTask崩溃