Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ C++;创建一个作业容器,您也可以添加函数,这些函数将在线程中启动,完成后将被删除_C++_Multithreading_Pthreads_C++17 - Fatal编程技术网

C++ C++;创建一个作业容器,您也可以添加函数,这些函数将在线程中启动,完成后将被删除

C++ C++;创建一个作业容器,您也可以添加函数,这些函数将在线程中启动,完成后将被删除,c++,multithreading,pthreads,c++17,C++,Multithreading,Pthreads,C++17,我想创建一个可以将函数推入其中的容器,该容器将在线程中立即启动。函数完成后,应自动将其从容器中删除,以便容器不会无限期增长 以下是我迄今为止的尝试: #include <thread> #include <future> #include <iostream> #include <map> class j_thread { std::thread thread; public: j_thread() {} templa

我想创建一个可以将函数推入其中的容器,该容器将在线程中立即启动。函数完成后,应自动将其从容器中删除,以便容器不会无限期增长

以下是我迄今为止的尝试:

#include <thread>
#include <future>
#include <iostream>
#include <map>

class j_thread {
    std::thread thread;
public:

    j_thread() {}

    template<typename F>
    j_thread(const F& f) : thread(f) {}

    j_thread& operator = (j_thread&& other) {
        this->thread.swap(other.thread);
        return *this;
    }

    virtual ~j_thread() {
        thread.join();
    }
};

class jobs {

    std::map<size_t, j_thread> threads;

public:

    template<typename F>
    void add_job(const F &function) {

        size_t job_id = threads.size();

        auto wrapped_function = [&function, job_id, this]() {
            function();
            threads.erase(job_id);
        };

        threads[job_id] = j_thread(wrapped_function);
    }

    void wait_for_all() {
        while(threads.size() != 0) {}
    }
};


int main() {

    jobs j;
    j.add_job([](){std::cout << "hello" << std::endl;});
    j.add_job([](){std::cout << "world" << std::endl;});
    j.wait_for_all();
}

在线程体中调用
join
是未定义的行为

查看以下各项的错误条件:

错误条件资源\u死锁\u如果此->获取\u id()== std::this_thread::get_id()(检测到死锁)

你的身体是:

    auto wrapped_function = [&function, job_id, this]() {
        function();
        threads.erase(job_id);
    };
在调用
erase
的地方,将调用
jthread
的dtor,该dtor调用可接合线程上的
join

在dtor中,您应该调用
detach
,而不是
join

为避免悬空,必须通过值捕获引用
函数

在调用
size
erase
时,您还必须添加一些互斥锁以避免map上的数据竞争:

std::mutex m;

int size() {
    std::lock_guard<std::mutex> lock{m};
    return threads.size();
}

auto wrapped_function = [f = function, job_id, this]() {
    f();
    std::lock_guard<std::mutex> l(m);
    threads.erase(job_id);
};

void wait_for_all() {
    while(size() != 0) {}
}
std::mutexm;
int size(){
std::lock_guard lock{m};
返回线程。size();
}
自动包装的_函数=[f=函数,作业_id,this](){
f();
标准:锁紧装置l(m);
线程。擦除(作业id);
};
void wait_for_all(){
而(size()!=0){}
}

在线程体中调用
join
是未定义的行为

查看以下各项的错误条件:

错误条件资源\u死锁\u如果此->获取\u id()== std::this_thread::get_id()(检测到死锁)

你的身体是:

    auto wrapped_function = [&function, job_id, this]() {
        function();
        threads.erase(job_id);
    };
在调用
erase
的地方,将调用
jthread
的dtor,该dtor调用可接合线程上的
join

在dtor中,您应该调用
detach
,而不是
join

为避免悬空,必须通过值捕获引用
函数

在调用
size
erase
时,您还必须添加一些互斥锁以避免map上的数据竞争:

std::mutex m;

int size() {
    std::lock_guard<std::mutex> lock{m};
    return threads.size();
}

auto wrapped_function = [f = function, job_id, this]() {
    f();
    std::lock_guard<std::mutex> l(m);
    threads.erase(job_id);
};

void wait_for_all() {
    while(size() != 0) {}
}
std::mutexm;
int size(){
std::lock_guard lock{m};
返回线程。size();
}
自动包装的_函数=[f=函数,作业_id,this](){
f();
标准:锁紧装置l(m);
线程。擦除(作业id);
};
void wait_for_all(){
而(size()!=0){}
}