码迷,mamicode.com
首页 > 其他好文 > 详细

无锁队列的实现

时间:2017-07-04 11:07:05      阅读:169      评论:0      收藏:0      [点我收藏+]

标签:目的   return   bool   oid   取出   读写   队列的实现   include   color   

锁是高性能程序的杀手,但是为了保证数据的一致性,在多线程的应用环境下又不得不加锁。但是在某些特殊的场景下, 是可以通过优化数据结构来达到无锁的目的。那么我们就来看一下如何实现一个无锁队列。

队列:众所周知,就是先进先出。 出队列的时候从队列头取出一个结点;入队列的时候,将结点添加到队列尾部。当多线程同时操作一个队列读写时,显然就需要加锁。但是在单读单写的这种多线程应用时,是可以做到无锁的。直接上代码

#ifndef _QUEUE_H_
#define _QUEUE_H_

template<class T>
class node
{ 
    public:
        T* pdata;
        node* next;    
};



template<class T>
class queue
{
    private:
        node<T> *front;
        node<T> *tear;
    public:
        queue();
        ~queue();
        bool isempty();
        T* pop();
        void push(T *p);
};



template<class T>
queue<T>::queue()
{
    node<T> *pnode = new node<T>();
    front  = pnode;
    tear = pnode;
}

template<class T>
queue<T>::~queue()
{
    node<T> *cur = front;
    node<T> *next = NULL;
    while(cur)
    {
        next = cur->next;
        delete cur->pdata;
        delete cur;
        cur = next;
    }
}

template<class T>
bool queue<T>::isempty()
{
    if(front == tear)
        return true;
    return false;
}



template<class T>
void queue<T>::push(T *p)
{
    node<T> *pnode = new node<T>();
    tear->pdata = p;
    tear->next = pnode;
    tear = pnode;
}


template<class T>
T* queue<T>::pop()
{
    if(isempty())
        return NULL;
    node<T>* pnode = front;
    T* p = pnode->pdata;
    front = front->next;
    delete pnode;
    return p;
}

#endif

下面是测试代码:

#include <stdio.h>
#include <pthread.h>
#include "queue.h"


void* fun1(void *p)
{
    queue<int> *q = (queue<int>*)p;
    int i = 0;
    while(1)
    {
        int *tmp = q->pop();
        if(tmp)
        {
            if(*tmp != i++)
                    printf("err\n");
            delete tmp;
        }
    }
}

void* fun2(void *p)
{
    queue<int> *q = (queue<int>*)p;
    int i = 0;
    while(1)
    {
        int *tmp = new int(i++);
        q->push(tmp);
    }
}

int main()
{
    queue<int> q;
    pthread_t t1,t2;
    pthread_create(&t1,NULL ,fun1 ,&q);
    pthread_create(&t2,NULL, fun2 ,&q);
    pthread_join(t1,NULL);
    pthread_join(t2,NULL);
    return 0;
}

原理其实很简单,就是在队列的末尾添加一个空节点。这样在队列非空的情况下,front结点与tear结点中间至少间隔一个结点。那么当两个线程同时插入与取出结点时,就不会存在同时操作front与tear的情况,从而保证不会出现race condition

 

无锁队列的实现

标签:目的   return   bool   oid   取出   读写   队列的实现   include   color   

原文地址:http://www.cnblogs.com/myd620/p/7114843.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!