多进程模型缺点
创建进程会带来一定开销
为了完成进程间通信数据交换、需要用到IPC技术。
上下文切换带来的时间开销
多线程优点
线程的创建和上下文切换的时间开销要比进程小得多
线程交换数据无需其他技术,利用数据区和堆区共享数据。
创建线程
#include<pthread.h>
#include<iostream>
#include<unistd.h>
using namespace std;
void *func( void*arg){}
int main()
{
pthread_t m_thread;
pthread_create(&m_thread,NULL,func,nullptr);
}
利用pyhread_create函数,赋值给线程id变量,并绑定其回调函数,其中第一个参数是线程id变量地址,第二个为传递线程属性的,传null为默认,第三个参数是函数地址,第四个为函数参数。
等待线程结束函数
void * thr_ret;
pthread_join(m_thread,&thr_ret);
该函数成功返回0,失败返回其他值。第一个参数是线程id地址,第二个参数是返回的回调函数的返回值。
在临界区内可调用的函数
线程安全函数:被多个线程同时调用不会引起问题。
非线程安全函数:被多个线程同时调用会引发问题。
一般线程安全函数后会加_r
线程同步
线程可能会出现多个线程访问同一块区域,导致读取错误的问题,于是我们要引入线程同步。
互斥量
#include<semaphore.h>
sem_t m_sem;
sem_init(&m_sem,0,1);
sem_destroy(&m_sem);
sem_post(&m_sem);
sem_wait(&m_sem);
定义一个信号量变量,使用sem_init进行初始化,其中第一个参数是信号量变量的地址,第二个变量传0是只允许一个线程内部使用,传递其他值可以创建多个进程共享的信号量。第三个参数是信号量初始值。
调用sem_post,信号量加一,调用sem_wait,信号量减一。
销毁线程的两种方式
pthread_join,等待线程终止并进行销毁。
pthread_detach,设置为分离线程,自动回收。