这是我自己写的一个拥有线程安全和阻塞功能的vector类SemVector(LINUX平台),欢迎大家使用
//semvector.h
#ifndef SEMVECTOR_H_
#define SEMVECTOR_H_
#include <pthread.h>
#include <unistd.h>
#include <semaphore.h>
#include <stdio.h>
template<class T>
class SemVector
{
private:
T *m_Array; //存储数据的向量
int m_Size; //向量的最大长度
int m_MaxSize;
pthread_mutex_t m_Mutex; //互斥锁
sem_t m_Empty;
sem_t m_Stored;
public:
SemVector(int size);
~SemVector();
//向vector尾部加入数据,若向量满了,则用条件变量等待
void PushBack(const T &elem);
//向vector尾部删除数据,若向量为空,则用条件变量等待
T PopBack();
//返回元素
T At(int i);
//返回数组的长度
int Size() { return m_Size; }
//返回数组是否为空
bool Empty() { return ( 0 == m_Size ); }
//返回数组的最大长度
int GetMaxSize() { return m_MaxSize; }
};
template<class T>
SemVector<T>::SemVector(int size)
{
m_MaxSize = size;
m_Size = 0;
m_Array = new T[size];
pthread_mutex_init(&m_Mutex, NULL);
sem_init(&m_Empty, 0, size);
sem_init(&m_Stored, 0, 0);
}
template<class T>
SemVector<T>::~SemVector()
{
delete m_Array;
pthread_mutex_destroy(&m_Mutex);
sem_destroy(&m_Empty);
sem_destroy(&m_Stored);
}
template<class T>
void SemVector<T>::PushBack(const T &elem)
{
sem_wait(&m_Empty);
pthread_mutex_lock(&m_Mutex);
m_Array[m_Size++] = elem;
#ifdef PRINT_DEBUG
printf("push: %d, size: %d, thread: %lu\n", elem, m_Size-1,
(unsigned long)pthread_self());
#endif
pthread_mutex_unlock(&m_Mutex);
sem_post(&m_Stored);
}
template<class T>
T SemVector<T>::PopBack()
{
T res;
sem_wait(&m_Stored);
pthread_mutex_lock(&m_Mutex);
res = m_Array[--m_Size];
#ifdef PRINT_DEBUG
printf("pop : %d, size: %d, thread: %lu\n", res, m_Size,
(unsigned long)pthread_self());
#endif
pthread_mutex_unlock(&m_Mutex);
sem_post(&m_Empty);
return res;
}
template<class T>
T SemVector<T>::At(int i)
{
T res;
pthread_mutex_unlock(&m_Mutex);
if( i < m_Size )
res = m_Array[i];
pthread_mutex_unlock(&m_Mutex);
return res;
}
#endif
以下是测试例子:
//测试例子
#define PRINT_DEBUG
#include "semvector.h"
SemVector<int> g_tvec(10);
int g_value = 1;
const int TCOUNT = 100;
//生产者线程
void *Producer(void *arg)
{
while(1)
{
g_tvec.PushBack(g_value++);
}
}
//消费者线程
void *Customer(void *arg)
{
while(1)
{
g_tvec.PopBack();
}
}
//主函数
int main()
{
pthread_t proid[TCOUNT], cusid[TCOUNT];
//产生10个生产者和10个消费者
for(int i=0; i<TCOUNT; i++)
{
pthread_create(&proid[i], NULL, Producer, NULL);
pthread_create(&cusid[i], NULL, Customer, NULL);
}
for(int i=0; i<TCOUNT; i++)
{
pthread_join(proid[i], NULL);
pthread_join(cusid[i], NULL);
}
return 0;
}