天天看點

C++兩種線程模式:委托和繼承(附示例)

委托版本使用非常簡單:

點選(此處)折疊或打開

static void hello(int m, int n)

{

    printf("[%u] hello: %d/%d\n", pthread_self(), m, n);

}

class X

public:

    void world(int m, int n, int l)

    {

        printf("[%u] X::world: %d/%d/%d\n", pthread_self(), m, n, l);

    }

};

int main()

    // 帶2個參數

    CThreadEngine engine9(bind(&hello, 2015, 5));

    // 帶3個參數

    CThreadEngine engine16(bind(&X::world, x2, 2016, 5, 3));

    return 0;

委托版本實作:

#ifndef MOOON_SYS_THREAD_ENGINE_H

#define MOOON_SYS_THREAD_ENGINE_H

// 如果測試,請不需注釋掉TEST_THREAD_ENGINE的定義

//#define TEST_THREAD_ENGINE 1

#if !defined(TEST_THREAD_ENGINE)

#include "mooon/sys/config.h" // 如果需要脫離mooon運作,請注釋掉這行

#endif // TEST_THREAD_ENGINE

#include pthread.h>

#include stdio.h>

#include unistd.h>

#if defined(TEST_THREAD_ENGINE)

#define SYS_NAMESPACE_BEGIN

#define SYS_NAMESPACE_END

SYS_NAMESPACE_BEGIN

// 基類

class Function

    virtual ~Function() {}

    virtual void operator ()() = 0;

////////////////////////////////////////////////////////////////////////////////

// 不帶參數

class FunctionWithoutParameter: public Function

    // 不使用傳回值,是以不需要傳回值,否則将void替換成需要的類型

    typedef void (*FunctionPtr)();

    FunctionWithoutParameter(FunctionPtr function_ptr)

        : _function_ptr(function_ptr)

    virtual void operator ()()

        (*_function_ptr)();

private:

    FunctionPtr _function_ptr;

template class ObjectType>

class MemberFunctionWithoutParameter: public Function

    typedef void (ObjectType::*MemberFunctionPtr)();

    MemberFunctionWithoutParameter(MemberFunctionPtr member_function_ptr, ObjectType* object)

        : _member_function_ptr(member_function_ptr), _object(object)

        (_object->*_member_function_ptr)();

    MemberFunctionPtr _member_function_ptr;

    ObjectType* _object;

// 帶1個參數

template typename ParameterType>

class FunctionWith1Parameter: public Function

    typedef void (*FunctionPtr)(ParameterType);

    FunctionWith1Parameter(FunctionPtr function_ptr, ParameterType parameter)

        : _function_ptr(function_ptr), _parameter(parameter)

        (*_function_ptr)(_parameter);

    ParameterType _parameter;

template class ObjectType, typename ParameterType>

class MemberFunctionWith1Parameter: public Function

    typedef void (ObjectType::*MemberFunctionPtr)(ParameterType);

    MemberFunctionWith1Parameter(MemberFunctionPtr member_function_ptr, ObjectType* object, ParameterType parameter)

        : _member_function_ptr(member_function_ptr), _object(object), _parameter(parameter)

        (_object->*_member_function_ptr)(_parameter);

// 帶2個參數

template typename Parameter1Type, typename Parameter2Type>

class FunctionWith2Parameter: public Function

    typedef void (*FunctionPtr)(Parameter1Type, Parameter2Type);

    FunctionWith2Parameter(FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2)

        : _function_ptr(function_ptr), _parameter1(parameter1), _parameter2(parameter2)

        (*_function_ptr)(_parameter1, _parameter2);

    Parameter1Type _parameter1;

    Parameter2Type _parameter2;

template class ObjectType, typename Parameter1Type, typename Parameter2Type>

class MemberFunctionWith2Parameter: public Function

    typedef void (ObjectType::*MemberFunctionPtr)(Parameter1Type, Parameter2Type);

    MemberFunctionWith2Parameter(MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2)

        : _member_function_ptr(member_function_ptr), _object(object), _parameter1(parameter1), _parameter2(parameter2)

        (_object->*_member_function_ptr)(_parameter1, _parameter2);

// 帶3個參數

template typename Parameter1Type, typename Parameter2Type, typename Parameter3Type>

class FunctionWith3Parameter: public Function

    typedef void (*FunctionPtr)(Parameter1Type, Parameter2Type, Parameter3Type);

    FunctionWith3Parameter(FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

        : _function_ptr(function_ptr), _parameter1(parameter1), _parameter2(parameter2), _parameter3(parameter3)

        (*_function_ptr)(_parameter1, _parameter2, _parameter3);

    Parameter3Type _parameter3;

template class ObjectType, typename Parameter1Type, typename Parameter2Type, typename Parameter3Type>

class MemberFunctionWith3Parameter: public Function

    typedef void (ObjectType::*MemberFunctionPtr)(Parameter1Type, Parameter2Type, Parameter3Type);

    MemberFunctionWith3Parameter(MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

        : _member_function_ptr(member_function_ptr), _object(object), _parameter1(parameter1), _parameter2(parameter2), _parameter3(parameter3)

        (_object->*_member_function_ptr)(_parameter1, _parameter2, _parameter3);

class Functor

    Functor()

        : _function(NULL)

    Functor(const Functor& other)

        _function = other._function;

        Functor& mutable_other = const_castFunctor&>(other);

        mutable_other._function = NULL;

    ~Functor()

        delete _function;

    Functor& operator =(const Functor& other)

        return *this;

    void operator ()()

        (*_function)();

    // 不帶參數

    Functor(FunctionWithoutParameter::FunctionPtr function_ptr)

        _function = new FunctionWithoutParameter(function_ptr);

    template class ObjectType>

    Functor(typename MemberFunctionWithoutParameterObjectType>::MemberFunctionPtr member_function_ptr, ObjectType* object)

        _function = new MemberFunctionWithoutParameterObjectType>(member_function_ptr, object);

    // 帶1個參數

    template typename ParameterType>

    Functor(typename FunctionWith1ParameterParameterType>::FunctionPtr function_ptr, ParameterType parameter)

        _function = new FunctionWith1ParameterParameterType>(function_ptr, parameter);

    template class ObjectType, typename ParameterType>

    Functor(typename MemberFunctionWith1ParameterObjectType, ParameterType>::MemberFunctionPtr member_function_ptr, ObjectType* object, ParameterType parameter)

        _function = new MemberFunctionWith1ParameterObjectType, ParameterType>(member_function_ptr, object, parameter);

    template typename Parameter1Type, typename Parameter2Type>

    Functor(typename FunctionWith2ParameterParameter1Type, Parameter2Type>::FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2)

        _function = new FunctionWith2ParameterParameter1Type, Parameter2Type>(function_ptr, parameter1, parameter2);

    template class ObjectType, typename Parameter1Type, typename Parameter2Type>

    Functor(typename MemberFunctionWith2ParameterObjectType, Parameter1Type, Parameter2Type>::MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2)

        _function = new MemberFunctionWith2ParameterObjectType, Parameter1Type, Parameter2Type>(member_function_ptr, object, parameter1, parameter2);

    template typename Parameter1Type, typename Parameter2Type, typename Parameter3Type>

    Functor(typename FunctionWith3ParameterParameter1Type, Parameter2Type, Parameter3Type>::FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

        _function = new FunctionWith3ParameterParameter1Type, Parameter2Type, Parameter3Type>(function_ptr, parameter1, parameter2, parameter3);

    template class ObjectType, typename Parameter1Type, typename Parameter2Type, typename Parameter3Type>

    Functor(typename MemberFunctionWith3ParameterObjectType, Parameter1Type, Parameter2Type, Parameter3Type>::MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

        _function = new MemberFunctionWith3ParameterObjectType, Parameter1Type, Parameter2Type, Parameter3Type>(member_function_ptr, object, parameter1, parameter2, parameter3);

    Function* _function;

Functor bind(FunctionWithoutParameter::FunctionPtr function_ptr)

    return Functor(function_ptr);

Functor bind(typename MemberFunctionWithoutParameterObjectType>::MemberFunctionPtr member_function_ptr, ObjectType* object)

    return Functor(member_function_ptr, object);

Functor bind(typename FunctionWith1ParameterParameterType>::FunctionPtr function_ptr, ParameterType parameter)

    return Functor(function_ptr, parameter);

Functor bind(typename MemberFunctionWith1ParameterObjectType, ParameterType>::MemberFunctionPtr member_function_ptr, ObjectType* object, ParameterType parameter)

    return Functor(member_function_ptr, object, parameter);

Functor bind(typename FunctionWith2ParameterParameter1Type, Parameter2Type>::FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2)

    return Functor(function_ptr, parameter1, parameter2);

Functor bind(typename MemberFunctionWith2ParameterObjectType, Parameter1Type, Parameter2Type>::MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2)

    return Functor(member_function_ptr, object, parameter1, parameter2);

Functor bind(typename FunctionWith3ParameterParameter1Type, Parameter2Type, Parameter3Type>::FunctionPtr function_ptr, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

    return Functor(function_ptr, parameter1, parameter2, parameter3);

Functor bind(typename MemberFunctionWith3ParameterObjectType, Parameter1Type, Parameter2Type, Parameter3Type>::MemberFunctionPtr member_function_ptr, ObjectType* object, Parameter1Type parameter1, Parameter2Type parameter2, Parameter3Type parameter3)

    return Functor(member_function_ptr, object, parameter1, parameter2, parameter3);

static void* thread_proc(void* parameter)

    Functor* functor = (Functor*)parameter;

    (*functor)();

    delete functor; // 記得這裡需要delete

    return NULL;

class CThreadEngine

    CThreadEngine(const Functor& functor)

        // bind()傳回的是一個臨時對象,

        // 故需要new一個,以便在thread_proc()過程中有效

        Functor* new_functor = new Functor(functor);

        int errcode = pthread_create(&_thread, NULL, thread_proc, new_functor);

        if (errcode != 0)

        {

            delete new_functor;

        }

    ~CThreadEngine()

        join();

    void join()

        if (_thread > 0)

            pthread_join(_thread, NULL);

            _thread = 0;

    CThreadEngine();

    CThreadEngine(const CThreadEngine&);

    CThreadEngine& operator =(const CThreadEngine&);

    pthread_t _thread;

// 以下為測試代碼

// 非類成員函數

static void hello()

    printf("[%u] hello\n", pthread_self());

static void world()

    printf("[%u] world\n", pthread_self());

static void hello(int m)

    printf("[%u] hello: %d\n", pthread_self(), m);

static void world(int m)

    printf("[%u] world: %d\n", pthread_self(), m);

static void world(int m, int n)

    printf("[%u] world: %d/%d\n", pthread_self(), m, n);

static void hello(int m, int n, int l)

    printf("[%u] hello: %d/%d/%d\n", pthread_self(), m, n, l);

static void world(int m, int n, int l)

    printf("[%u] world: %d/%d/%d\n", pthread_self(), m, n, l);

// 類成員函數

    //

    void hello()

        printf("[%u] X::hello\n", pthread_self());

    void world()

        printf("[%u] X::world\n", pthread_self());

    void hello(int m)

        printf("[%u] X::hello: %d\n", pthread_self(), m);

    void world(int m)

        printf("[%u] X::world: %d\n", pthread_self(), m);

    void hello(int m, int n)

        printf("[%u] X::hello: %d/%d\n", pthread_self(), m, n);

    void world(int m, int n)

        printf("[%u] X::world: %d/%d\n", pthread_self(), m, n);

    void hello(int m, int n, int l)

        printf("[%u] X::hello: %d/%d/%d\n", pthread_self(), m, n, l);

    CThreadEngine engine1(bind(&hello));

    CThreadEngine engine2(bind(&world));

    X* x1 = new X;

    X* x2 = new X;

    CThreadEngine engine3(bind(&X::hello, x1));

    CThreadEngine engine4(bind(&X::world, x2));

    CThreadEngine engine5(bind(&hello, 2015));

    CThreadEngine engine6(bind(&world, 2016));

    CThreadEngine engine7(bind(&X::hello, x1, 2015));

    CThreadEngine engine8(bind(&X::world, x2, 2016));

    CThreadEngine engine10(bind(&world, 2016, 5));

    CThreadEngine engine11(bind(&X::hello, x1, 2015, 5));

    CThreadEngine engine12(bind(&X::world, x2, 2016, 5));

    CThreadEngine engine13(bind(&hello, 2015, 5, 3));

    CThreadEngine engine14(bind(&world, 2016, 5, 3));

    CThreadEngine engine15(bind(&X::hello, x1, 2015, 5, 3));

    // 按任意鍵繼續繼續

    printf("Press ENTER to exit ...\n");

    getchar();

    engine1.join();

    engine2.join();

    engine3.join();

    engine4.join();

    engine5.join();

    engine6.join();

    engine7.join();

    engine8.join();

    engine9.join();

    engine10.join();

    engine11.join();

    engine12.join();

    engine13.join();

    engine14.join();

    engine15.join();

    engine16.join();

    delete x1;

    delete x2;

    // 按任意鍵繼續退出

SYS_NAMESPACE_END

#endif // MOOON_SYS_THREAD_ENGINE_H

繼續閱讀