SORU
9 AĞUSTOS 2013, Cuma


Packaged_task ve uyumsuz arasındaki fark nedir

C dişli modeli ile çalışırken 11, ben de fark ettim

std::packaged_task<int(int,int)> task([](int a, int b) { return a   b; });
auto f = task.get_future();
task(2,3);
std::cout << f.get() << '\n';

ve

auto f = std::async(std::launch::async, 
    [](int a, int b) { return a   b; }, 2, 3);
std::cout << f.get() << '\n';

tam olarak aynı şeyi yapıyor gibi. std::launch::deferred std::async koştum ama bu durumda büyük bir fark olabileceğini anlıyorum?

Bu iki yaklaşım arasındaki fark, ve daha da önemlisi, durumlar ne ben birini kullanın ne yapmalıyım?

CEVAP
9 AĞUSTOS 2013, Cuma


Eğer oldukça uzun bir işlevi kullanırsanız aslında bu örnek sadece gösterir farklar verdi gibi

//! sleeps for one second and returns 1
auto sleep = [](){
    std::this_thread::sleep_for(std::chrono::seconds(1));
    return 1;
};

Görev paketlenmiş

packaged_task kendi kendine çalışmıyor, onu çağırmak için:

std::packaged_task<int()> task(sleep);

auto f = task.get_future();
task(); // invoke the function

// You have to wait until task returns. Since task calls sleep
// you will have to wait at least 1 second.
std::cout << "You can see this after 1 second\n";

// However, f.get() will be available, since task has already finished.
std::cout << f.get() << std::endl;

std::async

Diğer taraftan, std::async launch::async farklı bir iş parçacığı görev çalıştırmayı deneyin

auto f = std::async(std::launch::async, sleep);
std::cout << "You can see this immediately!\n";

// However, the value of the future will be available after sleep has finished
// so f.get() can block up to 1 second.
std::cout << f.get() << "This will be shown after a second!\n";

Olumsuzluk

Ama her şey için async kullanmayı denemeden önce, geri gelecek future::~future bloklar: talep eden özel paylaşılan bir devlet olduğunu unutmayın

std::async(do_work1); // ~future blocks
std::async(do_work2); // ~future blocks

/* output: (assuming that do_work* log their progress)
    do_work1() started;
    do_work1() stopped;
    do_work2() started;
    do_work2() stopped;
*/

Eğer öyleyse gerçek asenkron istiyorsanız, geri tutmak için eğer şartlar değişirse sonuç için umurunda olsaydı zaten: 23 ** ya ihtiyacın var

{
    auto pizza = std::async(get_pizza);
    /* ... */
    if(need_to_go)
        return;          // ~future will block
    else
       eat(pizza.get());
}   

Bu konuda daha fazla bilgi için, Herb Sutter'ın madde sorunu tanımlayan async and ~future, ve Scott Meyer görmek görüşlerini açıklayan std::futures from std::async aren't special.

Diğer farklılıklar

std::async kullanarak edemezsiniz std::packaged_task başka bir iş için taşınmış olabilir, belirli bir iş parçacığı artık, Senin görevin çalıştırın.

std::packaged_task<int(int,int)> task(...);
auto f = task.get_future();
std::thread myThread(std::move(task),2,3);

std::cout << f.get() << "\n";

Ayrıca, bir packaged_task f.get(), program, aksi takdirde gelecekte daha hazır olacak gibi donar aramadan önce çağrılması gerekir:

std::packaged_task<int(int,int)> task(...);
auto f = task.get_future();
std::cout << f.get() << "\n"; // oops!
task(2,3);

TL;DR

Kullanım std::async eğer istediğiniz şeyler yapmış ve pek bakım bittiğinde, ve std::packaged_task isterseniz sar işler için onları taşımak için başka bir iş parçacığı veya ara onları daha sonra. Ya da, Christian alıntı için:

Sonunda bir std::packaged_task sadece bir alt düzey özelliği uygulama std::async (hangi neden olabilir daha önce std::async ile birlikte kullanılan diğer düşük seviyede şeyler gibi std::thread). Sadece std::packaged_task std::function std::future std::async std::packaged_task sarar aramalar bağlantılı bir sözlü (muhtemelen farklı bir iş parçacığı).

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • Chilla Frilla™

    Chilla Frill

    7 Aralık 2006
  • DancingIsAPassion

    DancingIsAPa

    29 AĞUSTOS 2009
  • Willie D.

    Willie D.

    16 Aralık 2006