我正在嘗試使用新的 jthreads 并開始std::jthread呼叫 operator() 的位置,但我無法讓它停止。我想通過將其作為函式物件呼叫來創建執行緒。
my_thrd = std::make_shared<std::jthread>(&Test::operator(), &test);
如果operater()我的 Test 類撰寫如下,它會編譯:
void Test::operator()()
{
using namespace std::literals;
while (!token.stop_requested()) {
std::cout << "Working ...\n" << std::flush;
std::this_thread::sleep_for(5s);
}
close_connection();
}
但由于它沒有停止,我想我需要以某種方式傳遞std::stop_token給class Test,就像這樣。
void Test::operator()(std::stop_token token) { ... }
但這不能編譯。我也確實更改了標題。
/usr/lib/gcc/x86_64-pc-linux-gnu/10.3.0/include/g -v10/thread: 在實體化 'static std::thread std::jthread::_S_create(std::stop_source&, _Callable&& , _Args&& ...) [with _Callable = void (Test:: )(std::stop_token); _Args = {Test }]': /usr/lib/gcc/x86_64-pc-linux-gnu/10.3.0/include/g -v10/thread:450:28: 來自'std::jthread::jthread( _Callable&&, _Args&& ...) [with _Callable = void (Test:: )(std::stop_token); _Args = {測驗};= void]' /usr/lib/gcc/x86_64-pc-linux-gnu/10.3.0/include/g -v10/bits/stl_construct.h:97:14: 來自'constexpr decltype (::new(void) *(0)) _Tp) std::construct_at(_Tp*, _Args&& ...) [與 _Tp = std::jthread; _Args = {void (Test:: )(std::stop_token), Test}; decltype (::new(void*(0)) _Tp) = std::jthread*]' /usr/lib/gcc/x86_64-pc-linux-gnu/10.3.0/include/g -v10/bits/alloc_traits .h:514:4: 來自 'static constexpr void std::allocator_traitsstd::allocator<_CharT >::construct(std::allocator_traitsstd::allocator<_CharT >::allocator_type&, _Up*, _Args&& ...) [ _Up = std::jthread; _Args = {void (Test:: )(std::stop_token), Test }; _Tp = std::jthread; std::allocator_traitsstd::allocator<_CharT >::allocator_type = std::allocatorstd::jthread]'
想法?
uj5u.com熱心網友回復:
您可以使用std::bindto bind &testto &Test::operator(),然后使用std::placeholders::_1to 為 unbound 保留一個位置std::stop_token:
struct Test {
void operator()(std::stop_token token) {
using namespace std::literals;
while (!token.stop_requested()) {
std::cout << "Working ...\n" << std::flush;
std::this_thread::sleep_for(5s);
}
}
};
int main() {
Test test;
auto my_thrd = std::make_shared<std::jthread>(
std::bind(&Test::operator(), &test, std::placeholders::_1));
}
演示。
正如@Nicol Bolas 評論的那樣,我們也可以使用 C 20std::bind_front來做到這一點,它比std::bind以下更輕量和直觀:
auto my_thrd = std::make_shared<std::jthread>(
std::bind_front(&Test::operator(), &test));
uj5u.com熱心網友回復:
一個簡單有效的解決方案是使用 lambda:
auto my_thrd = std::make_shared<std::jthread>(
[&test] (std::stop_token token) { test(token); });
并節省額外的費用和圖書館設施
演示
uj5u.com熱心網友回復:
jthread(或者thread,就此而言)接受任何可呼叫物件。這包括任何與一個operator()像... Test。
默認是按值傳遞;用于std::ref通過參考傳遞,但請注意,在這種情況下,您需要確保被參考的物件比執行緒存活的時間更長。
所以這只是:
auto my_thrd = std::make_shared<std::jthread>(test);
或(像原始代碼一樣通過參考傳遞):
auto my_thrd = std::make_shared<std::jthread>(std::ref(test));
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/325554.html
上一篇:兩個執行緒試圖訪問同一個串列:“System.ArgumentOutOfRangeException”
下一篇:如何在多核處理器中調度任務
