11-1和11-2的具体区别是什么?部分->部分什么是分离?在任何时间点,线程都可以连接或分离。可连接的线程可以被其他线程回收并杀死;它的内存资源(如栈)在被其他线程回收之前不会被释放。相反,一个detached线程不能被其他线程回收或杀死,它的内存资源在它终止时会被系统自动释放。线程的分离状态决定了线程如何终止自身。在上面的例子中,我们采用了线程的默认属性,即非分离状态(即可以组合,可连接,需要回收)。在这种情况下,原始线程等待创建的线程结束;只有当pthread_join()函数返回时,创建的线程才会终止,自己占用的系统资源才能释放。但是分离线程不是这样的,它不被其他线程等待,自己运行后,线程会被终止,系统资源会立即释放。程序员应该根据自己的需要选择合适的分离状态。总之,在使用pthread时,为了防止线程结束时线程资源被正确释放,从而避免潜在的内存泄漏,在线程结束时,确保线程处于分离状态,否则需要调用pthread_join()函数回收其资源。静态分配和动态分配?静态分配发生在程序被编译和链接时。动态分配发生在程序被调用和执行时。堆是动态分配的,没有静态分配的堆。栈的分配有两种方式:静态分配和动态分配。静态分配由编译器完成,就像局部变量的分配一样。动态分配由函数malloc分配。但是,栈的动态分配不同于堆。他的动态分配是编译器释放的,不需要我们手动实现。互斥锁mutex用于保证任何时候只有一个线程可以访问对象。当获取锁操作失败时,线程会进入休眠状态,等待锁被释放时被唤醒。mutex是一种线程互斥的自旋锁:自旋锁在任何时候都只能有一个线程访问对象。但是当获取锁操作失败时,它不会进入休眠状态,而是原地自旋,直到锁被释放。这样就节省了线程从休眠状态到唤醒的消耗,在加锁时间短的环境下会大大提高效率。但是如果加锁时间过长,会浪费CPU资源。读写锁:rwlock区分读和写,在读操作时,可以让多个线程同时获取读操作。但是同一时刻只有一个线程可以获得写锁。其他获取写锁失败的线程会进入休眠状态,直到写锁释放时被唤醒。注意:写锁会阻塞其他读写锁。当一个线程在写的时候获取了写锁,读锁不能被其他线程获取;写优先于读,当一个线程因为等待写锁而进入休眠状态时,后续的读者也必须等待适用于读数据的频率远大于写数据的场合。信号量:信号量用于线程间的同步。当一个线程完成操作后,通过信号量通知其他线程,然后其他线程可以继续执行某些操作。信号量用于线程间同步,即调度线程。超时的读写锁长时间未获取锁,返回ETIMEDOUT条件变量。条件变量是一种使用线程间共享的全局变量进行同步的机制。比如读者和作者的问题。当消息队列为空时,reader会使用pthread_cond_wait挂起,等待writer写入队列,并发送pthread_cond_signal,然后唤醒读取。请参阅图11-15了解UNIX环境中的高级编程。屏障是一种同步机制,供用户协调多个线程并行工作。屏障允许每个线程等待,直到所有协作线程都达到某个点,然后从该点继续执行。intpthread_barrier_init(pthread_barrier_t*restrictbarrier,constpthread_barrierattr_t*restrictattr,unsignedcount);在初始化屏障时,可以使用计数参数来指定在允许所有线程继续运行之前必须达到屏障的线程数。使用内存屏障强制语句前后的指令按照正确的顺序a++完成;b=f(a);C-;当上一句没有使用barrier时,可以按照下面的顺序执行。一个++;C-;b=f(a);但是没有问题。对象->数据=xxx;对象->准备好=1;设置好数据后,记下flag,然后在另一个线程中执行:if(obj->ready)do_something(obj->data);如果在设置数据之前设置标志,则结果是接收到do_something(unmodifiedobj->data)。这时候就需要强制执行语句的顺序。pthread_barrier_init(barrier,NULL,2);obj->data=xxx;obj->ready=1;pthread_barrier_wait(*barrier);pthread_barrier_wait(*barrier);if(obj->ready)do_something(obj->data);https://blog.csdn.net/迈克尔...
