C++异步编程

std::async和std::future创建后台任务并返回值

一,前言

std::async是一个函数模板,用来启动一个异步任务,启动起来的异步任务会返回一个std::futured对象,这个对象里面有异步任务的返回结果。

int func(){

    std::this_thread::sleep_for(std::chrono::seconds(1));
    return 0;
}

int main(){

    std::future<int> result = std::async(func);

    cout << result.get() << endl;

}
  1. 这里的result.get()和线程join()类似,程序会阻塞到当前行直到异步任务返回。想比线程我们可以拿到返回值
  2. 也可以使用result.wait()和join()一样,获取不到返回值

二,std::async 额外参数

  1. auto result = std::async(std::launch::deferred,func) // 一直延迟到主线程调用wait()或get()时才启动异步任务,如果主程序没有调用get()或wait(),则什么事没有发生
  2. auto result = std::async(std::launch::async,func) //系统必须创建出新线程
  3. auto result = std::async(std::launch::async | std::launch::deferred,func) //系统根据硬件资源决定是否创建线程
  4. auto result = std::async(func); 和3一样由系统决定

三,std::packaged_task类模板

int func(int a){

    std::this_thread::sleep_for(std::chrono::seconds(1));
    return a;
}
int main(){

    std::packaged_task<int(int)> mypt(func);
    std::thread t(std::ref(mypt),1);
    t.join();
    
    std::future<int> result = mypt.get_future(mypt);
    cout << result.get() << endl;
}

四,promise类模板

主要用于线程间通信

void func(std::promise<int>& tmp,int calc){

    //做一系列复杂的运算
    
    int result = calc;
    tmp.set_value(result);

}

void func2(std::future<int>& tmpf){
    auto result = tmpf.get();
    
    cout << result << endl;

}
int main(){

    std::promise<int> myprom;

    std::thread t(func,std::ref(myprom),100);

    t.join();
    std::future<int> ful = myprom.get_future();
    
    //auto result = ful.get();//只能get一次
    
    
    std::thread t2(func2,std::ref(ful));
    t2.join();

}

五,future成员函数

int func(){
    
    std::this_thread::sleep_for(std::chrono::seconds(1));
    return 1;
}

int main(){


    std::future<int> result = std::async(func);
    

    std::future _status status = result.wait_for(std::chrono::seconds(1));


    if(status == std::future_status::timeout){

        //异步任务超时还没有结束
        cout << result.get() << endl;

    }else if(status == std::future_status::ready){

        //异步任务成功返回
        cout << result.get() << endl; 

    }else if(status == std::future_status::deferred){
        //异步任务被延迟创建
        cout << result.get() << endl;//这会导致在主线程中执行线程入口函数,
        //个人感觉就跟调用普通函数是没啥区别
    }

}

六,shared_future类模板

由于get()函数被设计为移动语义,所以如果有多个线程想要获取函数线程返回值,就需要使用shared_future

int main(){


    std::packaged_task<int(int)> mypt(func);

    std::thread t1(std::ref(mypt));
    t1.join();

    std::shared_future<int> result_s(mypt.get_future());
    
    auto result = result_s.get();
    auto result2 = result_s.get(); //可以get多次
    
    std::thread t2(func,std::ref(result_s));
    t2.get();
}

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值