[英]VC++ implementation of std::promise
我對std :: promise的VC ++實現(Visual Studio 2015和2017)都有一個奇怪的問題。 set_value_at_thread_exit()似乎不像宣傳的那樣工作 - 或者我誤解了標准允許的內容以及標准不允許的內容。 以下代碼將在clang中編譯並運行正常但在使用VS2015(在第二個塊中)或VS2017(在第三個塊中)編譯時會崩潰:
#include <future>
#include <thread>
#include <iostream>
int main()
{
{
std::cout << "Safe version... ";
std::promise<int> promise;
auto f = promise.get_future();
std::thread
(
[](std::promise<int> p)
{
p.set_value(99);
},
std::move(promise)
)
.detach();
std::cout << f.get() << std::endl;
}
{
std::cout << "Will crash VS2015... ";
std::promise<int> promise;
auto f = promise.get_future();
std::thread(
[p{ std::move(promise) }]() mutable
{
p.set_value_at_thread_exit(99);
}
)
.detach();
std::cout << f.get() << std::endl;
}
{
std::cout << "Will crash VS2017... ";
std::promise<int> promise;
auto f = promise.get_future();
std::thread(
[](std::promise<int> p)
{
p.set_value_at_thread_exit(99);
},
std::move(promise)
)
.detach();
std::cout << f.get() << std::endl;
}
}
我試圖通過慷慨地使用換行符來顯示差異。
問題似乎是在MS實現中,即使調用了set_value_at_thead_exit(),lambda函數內的promise對象的析構函數也會嘗試使用'broken promise'異常更新共享狀態。 但是,這會失敗並依次拋出系統錯誤。 它在嘗試鎖定關聯的互斥鎖時發生。 如果未調用set_value_at_thread_exit(),則f.get()將按預期拋出future_error。
在MS實現(VS2017)內部,我發現代碼假裝檢查共享狀態是否在線程退出時就緒,但什么也沒做。 所以我想知道這是一個錯誤,還是我誤解了API,我應該確保承諾的生命周期延伸到線程退出之外。
后者似乎是VS2017在第二個代碼塊中發生的事情,但在VS2015中卻沒有 - 可能是由於std :: thread的實現差異?!
如上所述,代碼運行良好
clang: http : //rextester.com/FEZDS24592
gcc: http : //rextester.com/WFKE61563
但崩潰了
VS2015中的第二個塊: http: //rextester.com/NODVFO14840
和VS2017中的第三個塊。 這可以在這里測試: http : //webcompiler.cloudapp.net/
所以基本上我想知道我是否應該提出一個問題,或者我是否只是自欺欺人,因為我使用的語言都錯了?
謝謝
事實證明,xxx_at_thread_exit()在大多數當前實現中都存在問題。 有關詳細信息,請參閱此Visual Studio社區問題 。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.