window下的线程池

// 线程任务基类和线程池基类文件

#ifndef _ITHREADPOOL_H
#define _ITHREADPOOL_H

class IHandle
{
public:
    IHandle(){}
    virtual ~IHandle(){}
public:
    virtual void Run() = 0;
};

class IThreadPool
{
public:
    IThreadPool(){}
    virtual ~IThreadPool(){}
public:
    virtual void SetMaxNum(int iMaxNum) = 0;
public:
    virtual int  Start() = 0;
    virtual void Stop() = 0;
public:
    virtual int Dispatch(IHandle *pHandle) = 0;
};

#endif

// 线程池实现类头文件
#ifndef _THREADPOOL_H
#define _THREADPOOL_H

#include <Windows.h>
#include "CircleQueue.h"
#include "IThreadPool.h"

class CThreadPool : public IThreadPool
{   
public:
    CThreadPool();
    virtual ~CThreadPool();
public:
    void SetMaxNum(int iMaxNum);
public:
    int  Start();
    void Stop();
public:
    int Dispatch(IHandle *pHandle);
private:
    static DWORD WINAPI ThreadFun(LPVOID lParam);
private:
    bool m_bIsRun;
    int m_iMaxNum;
    HANDLE m_hStopEvent;
    CircleQueue m_Queue;
    CRITICAL_SECTION m_CS;
    CONDITION_VARIABLE m_ConVar;
};

#endif

// 线程池 实现类源文件
#include "ThreadPool.h"
#include <iostream>
using namespace std;

const int OK  = 0;
const int ERR = -1;

CThreadPool::CThreadPool() :
m_bIsRun(false),
m_iMaxNum(0)
{

}

CThreadPool::~CThreadPool()
{

}

void CThreadPool::SetMaxNum(int iMaxNum)
{
    m_iMaxNum = iMaxNum;
}

int CThreadPool::Start()
{
    int iRev = ERR;

    // 初始化
    m_bIsRun = true;
    InitializeConditionVariable(&m_ConVar);
    InitializeCriticalSection(&m_CS);

    // 创建线程
    HANDLE hThread = NULL;

    for (int i = 0; i < m_iMaxNum; i++)
    {
        hThread = CreateThread(NULL, 0, ThreadFun, this, 0, NULL);
        CloseHandle(hThread);
    }

    // 创建停止事件
    m_hStopEvent = CreateEvent(NULL, FALSE, FALSE, NULL);

    if (m_hStopEvent != NULL)
    {
        iRev = OK;
    }

    return iRev;
}

void CThreadPool::Stop()
{
    m_bIsRun = false;
    
    WakeAllConditionVariable(&m_ConVar);
    
    WaitForSingleObject(m_hStopEvent, INFINITE);
    CloseHandle(m_hStopEvent);
    m_hStopEvent = NULL;
    DeleteCriticalSection(&m_CS);
}

int CThreadPool::Dispatch(IHandle *pHandle)
{
    EnterCriticalSection(&m_CS);
    m_Queue.push(pHandle);
    LeaveCriticalSection(&m_CS);

    WakeConditionVariable(&m_ConVar);

    return 0;
}

DWORD WINAPI CThreadPool::ThreadFun(LPVOID lParam)
{
    IHandle *pIHandle = NULL;
    CThreadPool *pThreadPool = (CThreadPool *)lParam;
    
    while(pThreadPool->m_bIsRun)
    {
        EnterCriticalSection(&pThreadPool->m_CS);
       
        while(pThreadPool->m_Queue.getLength() == 0)
        {
            SleepConditionVariableCS(&pThreadPool->m_ConVar, &pThreadPool->m_CS, INFINITE);
            if (!pThreadPool->m_bIsRun) break;
        }
        
        pIHandle = (IHandle *)pThreadPool->m_Queue.pop();
        LeaveCriticalSection(&pThreadPool->m_CS);
        
        if (!pThreadPool->m_bIsRun)
        {
            delete pIHandle;
            break;
        }

        if (pIHandle != NULL)
        {
            pIHandle->Run();
            delete pIHandle;
        }
    }
    

   
    EnterCriticalSection(&pThreadPool->m_CS);

    if (--pThreadPool->m_iMaxNum == 0)
    {
        SetEvent(pThreadPool->m_hStopEvent);
        cout << pThreadPool->m_iMaxNum << endl;
    }
    
    LeaveCriticalSection(&pThreadPool->m_CS);
   

    return 0;
}

// 这里还使用到一个环形队列
// 头文件
#ifndef _CIRCLEQUEUE_H
#define _CIRCLEQUEUE_H

class CircleQueue
{
public:
    CircleQueue();
    virtual ~CircleQueue();
public:
    void push(void * item);
    void * pop();
    void * top();
    int getLength();

private:
    void ** mEntries;
    unsigned int mHead;     // 可以读的位置
    unsigned int mTail;     // 可以写的位置
    unsigned int mCount;    // 元素的个数
    unsigned int mMaxCount; // 总的数量
};

#endif

// 环形队列源文件
#include "CircleQueue.h"
#include "stdlib.h"
#include "memory.h"

CircleQueue :: CircleQueue()
{
    mMaxCount = 8;
    mEntries = (void**)malloc( sizeof( void * ) * mMaxCount );

    mHead = mTail = mCount = 0;
}

CircleQueue :: ~CircleQueue()
{
    free( mEntries );
    mEntries = NULL;
}

void CircleQueue :: push( void * item )
{
    if( mCount >= mMaxCount )
    {
        mMaxCount = ( mMaxCount * 3 ) / 2 + 1;
        void ** newEntries = (void**)malloc( sizeof( void * ) * mMaxCount );

        unsigned int headLen = 0, tailLen = 0;
        if( mHead < mTail )
        {
            headLen = mTail - mHead;
        }
        else
        {
            headLen = mCount - mTail;
            tailLen = mTail;
        }

        memcpy( newEntries, &( mEntries[ mHead ] ), sizeof( void * ) * headLen );
        if( tailLen )
        {
            memcpy( &( newEntries[ headLen ] ), mEntries, sizeof( void * ) * tailLen );
        }

        mHead = 0;
        mTail = headLen + tailLen;

        free( mEntries );
        mEntries = newEntries;
    }

    mEntries[ mTail++ ] = item;
    mTail = mTail % mMaxCount;
    mCount++;
}

void * CircleQueue :: pop()
{
    void * ret = NULL;

    if( mCount > 0 )
    {
        ret = mEntries[ mHead++ ];
        mHead = mHead % mMaxCount;
        mCount--;
    }

    return ret;
}

void * CircleQueue :: top()
{
    return mCount > 0 ? mEntries[ mHead ] : NULL;
}

int CircleQueue :: getLength()
{
    return mCount;
}

// main 函数实现 这里没有删除对象
#include <iostream>
#include "ThreadPool.h"
using namespace std;

class TestHandle : public IHandle
{
public:
    virtual void Run()
    {
        cout << GetCurrentThreadId() << "---------";
        cout << "Hello" << endl;
    }
};

int main()
{
    CThreadPool threadPool;
    threadPool.SetMaxNum(10);
    threadPool.Start();
   
    for (int i = 0; i < 100; i++)
    {
        threadPool.Dispatch(new TestHandle());
    }
    
    Sleep(1000*5);
    threadPool.Stop();
    
    return 0;
}

时间: 2024-10-13 21:34:35

window下的线程池的相关文章

linux下的线程池

什么时候需要创建线程池呢?简单的说,如果一个应用需要频繁的创建和销毁线程,而任务执行的时间又非常短,这样线程创建和销毁的带来的开销就不容忽视,这时也是线程池该出场的机会了.如果线程创建和销毁时间相比任务执行时间可以忽略不计,则没有必要使用线程池了. 下面是Linux系统下用C语言创建的一个线程池.线程池会维护一个任务链表(每个CThread_worker结构就是一个任务).   pool_init()函数预先创建好max_thread_num个线程,每个线程执thread_routine ()函

一个Linux下C线程池的实现

在传统服务器结构中, 常是 有一个总的 监听线程监听有没有新的用户连接服务器, 每当有一个新的 用户进入, 服务器就开启一个新的线程用户处理这 个用户的数据包.这个线程只服务于这个用户 , 当 用户与服务器端关闭连接以后, 服务器端销毁这个线程.然而频繁地开辟与销毁线程极大地占用了系统的资源.而且在大量用户的情况下, 系统为了开辟和销毁线程将浪费大量的时间和资源.线程池提供了一个解决外部大量用户与服务器有限资源的矛盾, 线程池和传统的一个用户对应一个线程的处理方法不同, 它的基本思想就是在程序

Linux下简单线程池的实现

线程池的技术背景 在面向对象编程中,创建和销毁对象是很费时间的,因为创建一个对象要获取内存资源或者其它更多资源.在Java中更是如此,虚拟机将试图跟踪每一个对象,以便能够在对象销毁后进行垃圾回收.所以提高服务程序效率的一个手段就是尽可能减少创建和销毁对象的次数,特别是一些很耗资源的对象创建和销毁.如何利用已有对象来服务(不止一个不同的任务)就是一个需要解决的关键问题,其实这就是一些"池化资源"技术产生的原因.比如大家所熟悉的数据库连接池正是遵循这一思想而产生的,本文将介绍的线程池技术同

linux 下c++线程池的简单实现(在老外代码上添加注释)

作为一个c++菜鸟,研究半天这个代码的实现原理,发现好多语法不太熟悉,因此加了一大堆注释,仅供参考.该段代码主要通过继承workthread类来实现自己的线程代码,通过thread_pool类来管理线程池,线程池不能够实现动态改变线程数目,存在一定局限性.目前可能还有缺陷,毕竟c++来封装这个东西,资源释放什么的必须想清楚,比如vector存储了基类指针实现多态,那么如何释放对象仍需要考虑,后续我可能会更进一步修改完善该代码,下面贡献一下自己的劳动成果. #include <pthread.h>

C++11下的线程池以及灵活的functional + bind + lamda

利用boost的thread实现一个线程类,维护一个任务队列,以便可以承载非常灵活的调用.这个线程类可以方便的为后面的线程池打好基础.线程池还是动态均衡,没有什么别的.由于minGW 4.7 对 C++11 thread 不支持,所以采用 boost 代替,linux 下是支持的,只是名字空间不同而已,套路都一样.先上代码: [cpp] view plaincopy #include #include <boost/thread/thread.hpp> #include <boost/t

Android下基于线程池的网络访问基础框架

引言 现在的Android开发很多都使用Volley.OkHttp.Retrofit等框架,这些框架固然有优秀的地方(以后会写代码学习分享),但是我们今天介绍一种基于Java线程池的网络访问框架. 实现思路及实现 APP界面上面的数据都是通过网络请求获取的,我们能不能将网络请求依次入队,然后配合着Java线程池,让线程依次处理我们的请求,最后返回结果给我们.下面我们先来看一下线程池工具类的实现: 1 public class ThreadPoolUtils { 2 3 private Threa

windows下利用线程池完成多任务的分配和运行

在做项目的过程中有时候为了提升效率,用了多线程的方法来对任务进行分割和应用,后来发现,采用线程池的方法能更好的利用线程资源来计算任务,网上有很多关于如何运行线程池的例子,msdn上也给出了对应的例子:https://msdn.microsoft.com/en-us/library/windows/desktop/ms686980(v=vs.85).aspx 感兴趣的话大家可以去看看,这里我给出一个简单的demo,利用线程池单次调用多次调用,例子如下: [cpp] view plain copy

Linux下简易线程池

线程池简介 简易线程池实现 线程池头文件threadpool.h如下: 1 #ifndef THREADPOOL_H 2 #define THREADPOOL_H 3 4 #include <stdio.h> 5 #include <stdlib.h> 6 #include <unistd.h> 7 #include <pthread.h> 8 9 /** 10 * 线程体数据结构 11 */ 12 typedef struct runner 13 { 14

5、java的concurrent包下的线程池

1.java.util.concurrent Class Executurs public class Executors extends Object 其中提供了返回类型为Executor.ExecutorService.ScheduledExecutorService.ThreadFactory和Callable的方法. public static ExecutorService newFixedThreadPool(int nThreads) 创建一个固定线程个数的线程池.当所有的线程都处