« | September 2025 | » | 日 | 一 | 二 | 三 | 四 | 五 | 六 | | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | | | | | |
| 公告 |
☆★☆★☆★☆★☆★☆ 生活的点点记录,以及一些体会...........
喜欢是淡淡的爱,爱是深深的喜欢.
时间会见证一切.......................
欢迎大家指出错误,共同进步..........
期待中..............................
☆★☆★☆★☆★☆★☆ |
Blog信息 |
blog名称: 日志总数:162 评论数量:312 留言数量:0 访问次数:947084 建立时间:2005年5月17日 |

| |
[Linux]pthead 学习 文章收藏
oceanblue 发表于 2009/5/19 21:14:06 |
#include <stdio.h>
#include <pthread.h>
#include <semaphore.h>
void *thread_a(void *in)
{
printf("I am thread_a\n");
pthread_exit((void *)0);
}
void *thread_b(void *in)
{
printf("I am thread_b\n");
pthread_exit((void *)0);
}
void *thread_c(void *in)
{
printf("I am thread_c\n");
pthread_exit((void *)0);
}
int main()
{
pthread_t a,b,c; /* thread id a, b, c*/
int val; /* used for function return result */
/* create thread a, b, c */
pthread_create(&a, NULL, thread_a, (void *)0);
pthread_create(&b, NULL, thread_b, (void *)0);
pthread_create(&c, NULL, thread_c, (void *)0);
/* main thread waits for termination of a,b,c */
pthread_join(a, (void **)0);
pthread_join(b, (void **)0);
pthread_join(c, (void **)0);
printf("Main thread is over\n");
return 0;
}在Linux下进行编译: gcc -o My_Thread My_Thread.c ./MyThread 得到的输出: I am thread_a I am thread_b I am thread_c Main thread is over 现在我们希望线程C的最先打印,然后线程B打印,最后线程A打印。即三个线程之间的打印有一定的先后关系。看下面程序:
#include <stdio.h>
#include <pthread.h>
#include <semaphore.h>
sem_t sem1;
sem_t sem2;
void *thread_a(void *in)
{
sem_wait(&sem1); /* wait for sem1 */
printf("I am thread_a\n");
pthread_exit((void *)0);
}
void *thread_b(void *in)
{
sem_wait(&sem2); /* wait for sem2 */
printf("I am thread_b\n");
sem_post(&sem1); /* increase sem1 by 1, make thread_a run*/
pthread_exit((void *)0);
}
void *thread_c(void *in)
{
printf("I am thread_c\n");
sem_post(&sem2); /* increase sem2 by 1, make thread_b run*/
pthread_exit((void *)0);
}
int main()
{
pthread_t a,b,c; /* thread id a, b, c*/
int val; /* used for function return result */
/* init sem1 sem2 to 0 , any thread waits for it will be blocked*/
sem_init(&sem1, 0, 0);
sem_init(&sem2, 0, 0);
/* create thread a, b, c */
pthread_create(&a, NULL, thread_a, (void *)0);
pthread_create(&b, NULL, thread_b, (void *)0);
pthread_create(&c, NULL, thread_c, (void *)0);
/* main thread waits for termination of a,b,c */
pthread_join(a, (void **)0);
pthread_join(b, (void **)0);
pthread_join(c, (void **)0);
/* destroy sem1 sem2 */
sem_destroy(&sem1);
sem_destroy(&sem2);
printf("Main thread is over\n");
return 0;
}
gcc -o My_thread1 My_thread1.c -lpthread./My_thread1I am thread_cI am thread_bI am thread_aMain thread is over可以见到,线程的执行顺序已经改变。
pthread便是大名鼎鼎的posix多线程库了.然而pthread的多线程基于C回调函数,在C++中应用是个不大方便的问题.由于c++的类成员函数指针是无法直接在pthread中回调的,因此,如果我们想要在C++中使用pthread多线程,必须要借助其他的技巧才可以做到.
首先,我们要兼容pthread的静态函数式回调,同时又要动态调用成员函数,因此,要有一个类负责转发调用,再次,我们考虑如何调用类,为了方便,我们用C++仿函数在线程内调用成员函数.
所以,首先我们想到实现一个ThreadCall类:
C++代码
class ThreadCall{
public:
static void *Fun(void *data){
//这儿如何定义呢?
}
};
我们这儿只能传入一个void*的数据,但是我们需要知道的数据呢?应该包括要调用的类,以及要传入的参数.同时,对这个类,我们还要求拥有仿函数接口,因此,我们做如下定义:
C++代码
//首先定义一个ThreadClass接口,所有回调类都直接或者间接继承自该类
//它规定了回调接口
class ThreadClass{
public:
virtual void *operator()(void *)=0;
};
C++代码
//再定义一个线程信息结构,其中包含了要调用的class和出入的数据
struct _threadInfo{
ThreadClass *threadClass;
void *data;
};
typedef _threadInfo ThreadInfo;
OK,再次回到我们的ThreadCall类,现在我们就可方便的写出它的实现了:
C++代码
class ThreadCall{
public:
static void *Fun(void *data){
ThreadInfo *info=(ThreadInfo *)data;
return info->threadClass->operator ()(info->data);
}
};
这样,我们就实现了C++式的使用pthread,虽然麻烦了点,但是实现了类成员函数线程调用,还是值得的.现在我们来测试下:
C++代码
class MyThreadClass : ThreadClass{
public:
virtual void *operator()(void *data){
char *str=(char *)data;
cout<<str<<endl;
return NULL;
};
};
int main(int argc,char *argv[]){
MyThreadClass threadClass;
ThreadInfo info;
info.threadClass=(ThreadClass *)&threadClass;
info.data="hello";
pthread_t pid;
pthread_create(&pid,NULL,&ThreadCall::Fun,&info);
system("pause");
}
执行程序,子线程成功打印出"hello"的信息. |
|
|