Best way for waiting for callback to finish

前端 未结 3 1692
渐次进展
渐次进展 2021-02-08 03:14

In the code below, main() function is calling request() function which inter call th_request_async() function which mm_th_done_cb().

What will be the best and efficient

相关标签:
3条回答
  • 2021-02-08 03:41

    You can use std::promise:

    std::promise<int> promise;
    
    int mm_th_done_cb(int error_code, th_result_s* th_result, void* user_data)
    {
        promise.set_value(error_code /*this value will be returned by the future.get()*/);
        return 0;
    }
    
    int main()
    {
        std::future<int> future = promise.get_future();
        request();
        int value = future.get();
        return 0;
    }
    

    If you don't need to return any value from the callback, then you can use a std::promise<void> and std::future<void> pair.

    Both examples in wuqiang's answer are wrong.

    1.

    #include <future>
    int main()
    {
        request();
    
        // WRONG: Here we don't want to call 'mm_th_done_cb' ourselves.
        std::future<int> myFuture = std::async(mm_th_done_cb);
    
        //wait until mm_th_done_cb has been excuted;
        int result = myFuture.get();
    }
    

    2.

    #include <condition_variable>
    
    std::mutex mtx;
    std::condition_variable cv;
    
    int mm_th_done_cb(int error_code, th_result_s* th_result, void*     user_data)
    {
        cv.notify_one();
        return 0;
    }
    
    int main()
    {
        request();
    
        // WRONG: If the 'request' finishes quickly, then the 'mm_th_done_cb'
        // callback will be called and will notify the condition variable before 
        // the following lines execute, i.e. before the main thread starts 
        // waiting on the condition variable. Thus the 'cv.wait(lck)' will 
        // never return.
    
        unique_lock<std::mutex> lck(mtx);
        cv.wait(lck);
        return 0;
    }
    
    0 讨论(0)
  • 2021-02-08 03:42

    If C++11 is available,you can std::future

    #include <future>
    int main()
    {
        request();
        std::future<int> myFuture = std::async(mm_th_done_cb);
        //wait until mm_th_done_cb has been excuted;
        int result = myFuture.get();
    }
    

    or you can use synchronization mechanism.such as condition_variable,which is cross-platform.

    #include <condition_variable>
    std::mutex mtx;
    std::condition_variable cv;
    int mm_th_done_cb(int error_code, th_result_s* th_result, void* user_data)
    {
        cv.notify_one();
        return 0;
    }
    
    int main()
    {
        request();
        unique_lock<std::mutex> lck(mtx);
        cv.wait(lck);
        return 0;
    }
    
    0 讨论(0)
  • 2021-02-08 03:49

    You can use RegisterWaitForSingleObject

    0 讨论(0)
提交回复
热议问题