在 C++20 中使用 std::jthread 和逗号运算符并行执行多个操作
Executing several actions in parallel with std::jthread and comma operator in C++20
在 C++20 中我们得到了一个新的线程-class std::jthread
不同于旧的 std::thread
waits
用于析构函数中的线程终止。因此,使用未命名的 jthread 对象和逗号运算符并行执行多个操作变得容易:
#include <thread>
#include <iostream>
int main() {
std::jthread{ []{ std::cout << "Hello from new thread\n"; } },
std::cout << "Hello from main thread\n";
}
这很好用,演示:https://gcc.godbolt.org/z/YPW8bq7jK
很遗憾,Visual Studio2019在这里发出警告:
warning C4834: discarding return value of function with 'nodiscard' attribute
因为std::jthread
构造函数在里面声明为[[nodiscard]]
。据我所知,标准不需要此属性:https://timsong-cpp.github.io/cppwp/n4861/thread.jthread.class.
这只是 MSVC STL 中的一个错误,还是确实存在与这种 jthread
用法相关的风险?
为什么不这样写呢?
#include <thread>
#include <iostream>
int main()
{
// Note: Just like the original
// It is indeterminate what order these are
// printed out in.
std::jthread parallelThread{ []{ std::cout << "Hello from new thread\n"; } };
std::cout << "Hello from main thread\n";
}
这完全一样,但使用命名变量而不是不可见的临时变量。
作为旁注,您可以通过确保知道 jthread
何时被销毁来强制执行命令。
#include <thread>
#include <iostream>
int main()
{
{
std::jthread parallelThread{ []{ std::cout << "Hello from new thread\n"; } };
}
std::cout << "Hello from main thread\n";
}
there is really some risk associated with such jthread-usage?
定义“此类用途”和“一些风险”。
nodiscard
属性完全适合 jthread
的构造函数。是的,您 可以 编写代码,其中创建和丢弃 jthread
对象是一件有意义的、实用的事情。但即使它有意义且实用,您仍然不应该这样做。它以一种绝对不会增加任何价值的方式在您的代码中变得可爱。它看起来 像一个错误,最好不要编写看起来与损坏代码几乎相同的代码。
尝试编写清晰、干净的代码,不需要有人知道 C++ 逗号运算符及其与子表达式的关系的详细信息,以便准确地衡量其操作。
是的,标准库实现可以出于任何原因发出警告。只要格式正确的程序按照标准的描述成功编译和执行,实现就是有效的。
在 C++20 中我们得到了一个新的线程-class std::jthread
不同于旧的 std::thread
waits
用于析构函数中的线程终止。因此,使用未命名的 jthread 对象和逗号运算符并行执行多个操作变得容易:
#include <thread>
#include <iostream>
int main() {
std::jthread{ []{ std::cout << "Hello from new thread\n"; } },
std::cout << "Hello from main thread\n";
}
这很好用,演示:https://gcc.godbolt.org/z/YPW8bq7jK
很遗憾,Visual Studio2019在这里发出警告:
warning C4834: discarding return value of function with 'nodiscard' attribute
因为std::jthread
构造函数在里面声明为[[nodiscard]]
。据我所知,标准不需要此属性:https://timsong-cpp.github.io/cppwp/n4861/thread.jthread.class.
这只是 MSVC STL 中的一个错误,还是确实存在与这种 jthread
用法相关的风险?
为什么不这样写呢?
#include <thread>
#include <iostream>
int main()
{
// Note: Just like the original
// It is indeterminate what order these are
// printed out in.
std::jthread parallelThread{ []{ std::cout << "Hello from new thread\n"; } };
std::cout << "Hello from main thread\n";
}
这完全一样,但使用命名变量而不是不可见的临时变量。
作为旁注,您可以通过确保知道 jthread
何时被销毁来强制执行命令。
#include <thread>
#include <iostream>
int main()
{
{
std::jthread parallelThread{ []{ std::cout << "Hello from new thread\n"; } };
}
std::cout << "Hello from main thread\n";
}
there is really some risk associated with such jthread-usage?
定义“此类用途”和“一些风险”。
nodiscard
属性完全适合 jthread
的构造函数。是的,您 可以 编写代码,其中创建和丢弃 jthread
对象是一件有意义的、实用的事情。但即使它有意义且实用,您仍然不应该这样做。它以一种绝对不会增加任何价值的方式在您的代码中变得可爱。它看起来 像一个错误,最好不要编写看起来与损坏代码几乎相同的代码。
尝试编写清晰、干净的代码,不需要有人知道 C++ 逗号运算符及其与子表达式的关系的详细信息,以便准确地衡量其操作。
是的,标准库实现可以出于任何原因发出警告。只要格式正确的程序按照标准的描述成功编译和执行,实现就是有效的。