3.基于对象的编程风格

1. 说明:

此博客记录如何以基于对象的方式进行编程,分别以旧的和最新的C++版本进行实现
面向对象:子类继承父类,实现父类提供的虚函数
基于对象:子类中包含一个父类的成员变量,同时子类中编写实际函数,并在子类构造函数内将实际函数以回调函数的形式注册到父类成员变量中

2. 相关代码:

使用旧的C++版本实现:

2.1 Thread.h
#ifndef _THREAD_H_
#define _THREAD_H_

#include <pthread.h>
#include <boost/function.hpp>
#include <boost/bind.hpp>

class Thread
{
    
    
public:
    //别名
    using ThreadFunc = boost::function<void()>;

    explicit Thread(const ThreadFunc& func);
    virtual ~Thread();

    void Start();
    void Join();

    void SetAutoDelete(bool autoDelete);

private:
    static void* ThreadRoutine(void* arg);
    void Run();
    pthread_t _threadId;
    //回调函数
    ThreadFunc _func;
    bool _autoDelete;
};

#endif
2.2 Thread.cpp
#include "Thread.h"
#include <iostream>
using namespace std;

Thread::Thread(const ThreadFunc& func) : _func(func),_autoDelete(false)
{
    
    
    cout << "Thread() ..." << endl;
}

Thread:: ~Thread()
{
    
    
    cout << "~Thread() ..." << endl;
}

void Thread::Start()
{
    
    
    //创建一个线程,指定线程入口函数ThreadRoutine,参数为this指针(指向实际对象本身)
    pthread_create(&_threadId, nullptr, ThreadRoutine, this);
}
void Thread::Join()
{
    
    
    //以阻塞的形式等待指定的线程终止
    pthread_join(_threadId,nullptr);
}

void* Thread::ThreadRoutine(void* arg)
{
    
    
    //将传递过来的对象指针转换为Thread*(基类)类型
    //即基类指针thread指向了派生类对象
    Thread* thread = static_cast<Thread*>(arg);
    //利用虚函数多态,使用基类指针调用子类对象的函数
    //也可以理解为此时的基类相当于一个库,回调了子类中的虚函数
    thread->Run();
    //当子类对象run函数执行完毕后,自动删除当前线程
    if(thread->_autoDelete){
    
    
        delete thread;
    }
    return nullptr;
}

void Thread::SetAutoDelete(bool autoDelete)
{
    
    
    _autoDelete = autoDelete;
}

void Thread::Run()
{
    
    
    _func();
}
2.3 Thread_test.cpp
#include "Thread.h"
#include <iostream>
#include <unistd.h>
#include <boost/function.hpp>

using namespace std;

class Foo
{
    
    
public:
    Foo(int count) : _count(count)
    {
    
    
    }
    
    void MemberFunc()
    {
    
    
        while (_count--)
        {
    
    
            cout << "this is a test ..." << endl;
            sleep(1);
        }
        
    }

    void MemberFunc2(int x)
    {
    
    
        while (_count--)
        {
    
    
            cout << "x = " << x << " this is a test2 ..." << endl;
            sleep(1);
        }
        
    }
    int _count;
};


void ThreadFunc()
{
    
    
    cout << "TestFunc() ..." << endl;
}

void ThreadFunc2(int count)
{
    
    
    while(count--)
    {
    
    
        cout << "TestFunc2() ..." << endl;
        sleep(1);
    }
    
}

int main()
{
    
    
    //绑定无参全局函数
    Thread t1(ThreadFunc);
    //绑定带参全局函数
    Thread t2(boost::bind(ThreadFunc2, 5));
    Foo foo(3);
    //绑定无参类成员函数
    Thread t3(boost::bind(&Foo::MemberFunc, &foo));
    //绑定带参类成员函数
    Foo foo2(3);
    Thread t4(boost::bind(&Foo::MemberFunc2, &foo2, 20));

    t1.Start();
    t2.Start();
    t3.Start();
    t4.Start();

    t1.Join();
    t2.Join();
    t3.Join();
    t4.Join();

    return 0;
}

使用C++17版本实现:

2.4 Thread_new.h
#ifndef _THREAD_NEW_H_
#define _THREAD_NEW_H_

#include <functional>
#include <string>
#include <thread>

class ThreadNew{
    
    
public:
    using ThreadFunc = std::function<void()>;

    explicit ThreadNew(const ThreadFunc &func, const std::string &name = {
    
    });
    ~ThreadNew();

    void start();
    void join();

private:
    ThreadFunc _func;
    std::string _name;
    std::unique_ptr<std::thread> _thread;
    bool _started;
    bool _joined;
};


#endif
2.5 Thread_new.cpp
#include "Thread_new.h"
#include <iostream>
#include <cassert>


ThreadNew::ThreadNew(const ThreadFunc& func, const std::string &name) : 
    _func{
    
    std::move(func)},
    _name{
    
    name.empty() ? "ThreadNew" : name},
    _thread{
    
    },
    _started{
    
    false},
    _joined{
    
    false}
{
    
    
    std::cout << _name << " ThreadNew()..." << " constructed." << std::endl;
}

ThreadNew::~ThreadNew()
{
    
    
    if (_started && _joined) {
    
    
        _thread->detach();//分离子线程
    }
    std::cout <<  _name << " ~ThreadNew()..." << " destructed." << std::endl;
}

void ThreadNew::start()
{
    
    
    assert(!_started);//断言,条件为假时中止程序并报错
    _started = true;
    try
    {
    
    
    	//使用智能指针管理线程,可自动销毁
        _thread = std::make_unique<std::thread>([this](){
    
    
            _func();
        });
    }
    catch(const std::exception& e)
    {
    
    
        _started = false;
        std::cerr << e.what() << '\n';
    }
    
}

void ThreadNew::join()
{
    
    
    assert(_started);
    if (_joined) {
    
    
        std::cout << _name << " has already started." << std::endl;
        return;
    }else {
    
    
        std::cout << _name << " going to be joined." << std::endl;
    }
    assert(!_joined);
    _joined = true;
    if(!_thread->joinable()){
    
    
        return;
    }
    _thread->join();
}

2.6 Thread_new_test.cpp
#include "Thread_new.h"

#include <iostream>

class Foo
{
    
    
public:
    Foo(int count) : _count{
    
    count} {
    
    }

    void MemberFunc() {
    
    
        while (_count--) 
        {
    
    
            std::cout << "This is a test ..." << std::endl;
        }
    }

    void MemberFunc2(int x) {
    
    
        while (_count--) 
        {
    
    
            std::cout << "x = " << x << " This is a test2 ..." << std::endl;
        }
    }

private:
    int _count;
};

void ThreadFunc()
{
    
    
    std::cout << "ThreadFunc() ..." << std::endl;
}

void ThreadFunc2(int j)
{
    
    
    std::cout << "j = " << j <<"ThreadFunc2() ..." << std::endl;
}

int main()
{
    
    
    //绑定无参全局函数
    ThreadNew t1([](){
    
     ThreadFunc(); }, "t1"); //使用lambda表达式注册回调函数
    //绑定带参全局函数
    ThreadNew t2([](){
    
     ThreadFunc2(3); }, "t2");
    Foo foo(3);
    //绑定无参类成员函数
    ThreadNew t3([&foo](){
    
     foo.MemberFunc(); }, "t3");
    //绑定带参类成员函数
    Foo foo2(3);
    ThreadNew t4([&foo2](){
    
     foo2.MemberFunc2(4); }, "t4");

    t1.start();
    t2.start();
    t3.start();
    t4.start();

    t1.join();
    t2.join();
    t3.join();
    t4.join();
    return 0;
}

猜你喜欢

转载自blog.csdn.net/FY_13781298928/article/details/134876993