QtFuture 命名空间
头文件 | #include <QFuture> |
CMake | find_package(Qt6 REQUIRED COMPONENTS Core) target_link_libraries(mytarget PRIVATE Qt6::Core) |
qmake | QT += core |
类
(自 6.3) struct | WhenAnyResult |
类型
(自 6.0) enum class | Launch { Sync, Async, Inherit } |
函数
QFuture<QtFuture::ArgsType<Signal>> | connect(Sender *sender, Signal signal) |
(自 6.1) QFuture<T> | makeExceptionalFuture(const QException &exception) |
(自 6.1) QFuture<T> | makeExceptionalFuture(std::__exception_ptr::exception_ptr exception) |
(自 6.6) QFuture<QtFuture::ContainedType<Container>> | makeReadyRangeFuture(Container &&container) |
(自 6.6) QFuture<ValueType> | makeReadyRangeFuture(std::initializer_list<ValueType> values) |
(自 6.6) QFuture<std::decay_t<T>> | makeReadyValueFuture(T &&value) |
(自 6.6) QFuture<void> | makeReadyVoidFuture() |
(自 6.3) QFuture<OutputSequence> | whenAll(InputIt first, InputIt last) |
(自 6.3) QFuture<OutputSequence> | whenAll(Futures &&... futures) |
(自 6.3) QFuture<QtFuture::WhenAnyResult<T>> | whenAny(InputIt first, InputIt last) |
(自 6.3) QFuture<std::variant<std::decay_t<Futures>...>> | whenAny(Futures &&... futures) |
类型文档
[since 6.0]
enum class QtFuture::Launch
表示运行 QFuture 后续操作的执行策略。
常量 | 值 | 描述 |
---|---|---|
QtFuture::Launch::Sync | 0 | 后续将启动在执行与未来相关的承诺的同一线程上,或者如果已经完成,则将在执行 then() 的线程中立即调用后续。 |
QtFuture::Launch::Async | 1 | 后续将在从全局 QThreadPool 中获取的单独线程中启动。 |
QtFuture::Launch::Inherit | 2 | 后续将继承其附加的未来的启动策略或线程池。 |
Sync
被用作默认启动策略。
此枚举是在 Qt 6.0 中引入的。
另请参阅QFuture::then() 和 QThreadPool::globalInstance。
函数文档
模板 <typename Sender, typename Signal, typename = QtPrivate::EnableIfInvocable<Sender, Signal>> QFuture<QtFuture::ArgsType<Signal>> QtFuture::connect(Sender *sender, Signal signal)
创建并返回一个 QFuture,当 sender 发射 signal 时将可用。如果 signal 没有参数,返回 QFuture<void>。如果 signal 只接受一个参数,结果 QFuture 将用信号参数的值填充。如果 signal 接受多个参数,结果 QFuture 将用存储信号参数值的 std::tuple 填充。如果 sender 在 signal 发射之前被销毁,结果 QFuture 将被取消。
例如,假设我们有以下对象
class Object : public QObject { Q_OBJECT ... signals: void noArgSignal(); void singleArgSignal(int value); void multipleArgs(int value1, double value2, const QString &value3); };
我们可以以以下方式将其信号连接到 QFuture 对象
Object object; QFuture<void> voidFuture = QtFuture::connect(&object, &Object::noArgSignal); QFuture<int> intFuture = QtFuture::connect(&object, &Object::singleArgSignal); using Args = std::tuple<int, double, QString>; QFuture<Args> tupleFuture = QtFuture::connect(&object, &Object::multipleArgs)
我们还可以将后续链接,以在信号发射时运行
QtFuture::connect(&object, &Object::singleArgSignal).then([](int value) { // do something with the value });
您也可以使用 QtFuture::Launch 策略在新的线程或自定义线程池中启动后续。例如
QtFuture::connect(&object, &Object::singleArgSignal).then(QtFuture::Launch::Async, [](int value) { // this will run in a new thread });
如果 Qt 的信号-槽连接槽调用抛出异常,如果没有在槽中处理,则视为未定义行为。但是通过 QFuture::connect(),您可以在后续中抛出和处理异常
QtFuture::connect(&object, &Object::singleArgSignal).then([](int value) { ... throw std::exception(); ... }).onFailed([](const std::exception &e) { // handle the exception }).onFailed([] { // handle other exceptions });
注意:连接的未来只有在信号第一次发射时才会完全实现。
另请参阅QFuture 和 QFuture::then。
[since 6.1]
模板 <typename T = void> QFuture<T> QtFuture::makeExceptionalFuture(const QException &exception)
创建并返回一个已经包含异常 exception 的 QFuture。
QException e; auto f = QtFuture::makeExceptionalFuture<int>(e); ... try { f.result(); // throws QException } catch (QException &) { // handle exception here }
此函数是在 Qt 6.1 中引入的。
另请参阅QFuture,QException,QtFuture::makeReadyVoidFuture() 和 QtFuture::makeReadyValueFuture。
[since 6.1]
模板 <typename T = void> QFuture<T> QtFuture::makeExceptionalFuture(std::__exception_ptr::exception_ptr exception)
这是一个重载函数。
创建并返回一个已经包含异常 exception 的 QFuture。
struct TestException { }; ... auto exception = std::make_exception_ptr(TestException()); auto f = QtFuture::makeExceptionalFuture<int>(exception); ... try { f.result(); // throws TestException } catch (TestException &) { // handle exception here }
此函数是在 Qt 6.1 中引入的。
另请参阅QFuture,QException,QtFuture::makeReadyVoidFuture() 和 QtFuture::makeReadyValueFuture。
[自6.6起]
模板 <typename Container, QtFuture::if_container_with_input_iterators<Container> = true> QFuture<QtFuture::ContainedType<Container>> QtFuture::makeReadyRangeFuture(Container &&container)
这是一个重载函数。
接受一个输入容器 container 并返回一个包含从 container 值初始化的多个结果的 QFuture。
注意:此重载仅在 Container
具有输入迭代器时参与重载解析。
const std::vector<int> values{1, 2, 3}; auto f = QtFuture::makeReadyRangeFuture(values); ... const int count = f.resultCount(); // count == 3 const auto results = f.results(); // results == { 1, 2, 3 }
此函数是在 Qt 6.6 中引入的。
另请参阅:QFuture、QtFuture::makeReadyVoidFuture()、QtFuture::makeReadyValueFuture() 和 QtFuture::makeExceptionalFuture。
[自6.6起]
模板 <typename ValueType> QFuture<ValueType> QtFuture::makeReadyRangeFuture(std::initializer_list<ValueType> values)
这是一个重载函数。
返回一个包含从输入初始化列表 values 初始化的多个结果的 QFuture。
auto f = QtFuture::makeReadyRangeFuture({1, 2, 3}); ... const int count = f.resultCount(); // count == 3 const auto results = f.results(); // results == { 1, 2, 3 }
此函数是在 Qt 6.6 中引入的。
另请参阅:QFuture、QtFuture::makeReadyVoidFuture()、QtFuture::makeReadyValueFuture() 和 QtFuture::makeExceptionalFuture。
[自6.6起]
模板 <typename T> QFuture<std::decay_t<T>> QtFuture::makeReadyValueFuture(T &&value)
创建并返回一个已经包含结果 value 的 QFuture。返回的 QFuture 类型为 std::decay_t<T>,其中 T 不为 void。返回的 QFuture 将已在完成状态。
auto f = QtFuture::makeReadyValueFuture(std::make_unique<int>(42)); ... const int result = *f.takeResult(); // result == 42
此函数是在 Qt 6.6 中引入的。
另请参阅:QFuture、QtFuture::makeReadyRangeFuture()、QtFuture::makeReadyVoidFuture() 和 QtFuture::makeExceptionalFuture。
[自6.6起]
QFuture<void> QtFuture::makeReadyVoidFuture()
创建并返回一个空 QFuture。这种 QFuture 无法存储任何结果。它可以用作查询计算的状态。返回的 QFuture 将已在完成状态。
auto f = QtFuture::makeReadyVoidFuture(); ... const bool started = f.isStarted(); // started == true const bool running = f.isRunning(); // running == false const bool finished = f.isFinished(); // finished == true
此函数是在 Qt 6.6 中引入的。
另请参阅:QFuture、QFuture::isStarted()、QFuture::isRunning()、QFuture::isFinished()、QtFuture::makeReadyValueFuture()、QtFuture::makeReadyRangeFuture 和 QtFuture::makeExceptionalFuture。
[自6.3起]
模板 <typename OutputSequence, typename InputIt> QFuture<OutputSequence> QtFuture::whenAll(InputIt first, InputIt last)
返回一个新的QFuture,当从first到last的所有future完成时,该future将成功。 first和last是类型为T
的future封装类型序列的迭代器。 OutputSequence
是一个包含从first到last的所有完成future的序列,出现的顺序与输入相同。如果未指定OutputSequence
的类型,则将返回包含QFuture<T>
的QList
中的结果future。例如
QList<QFuture<int>> inputFutures {...}; // whenAll has type QFuture<QList<QFuture<int>>> auto whenAll = QtFuture::whenAll(inputFutures.begin(), inputFutures.end()); // whenAllVector has type QFuture<std::vector<QFuture<int>>> auto whenAllVector = QtFuture::whenAll<std::vector<QFuture<int>>>(inputFutures.begin(), inputFutures.end());
注意:输出序列必须支持随机访问和resize()
操作。
如果first
等于last
,则此函数返回一个包含空OutputSequence
的已准备好QFuture。
返回的未来总是在所有指定的future完成后才成功完成。无论这些future中的哪个完成时出错或被取消,都没有关系。您可以在whenAll()
返回的未来之后使用.then()
来处理已完成的future。
QList<QFuture<int>> inputFutures {...}; QtFuture::whenAll(inputFutures.begin(), inputFutures.end()) .then([](const QList<QFuture<int>> &results) { for (auto future : results) { if (future.isCanceled()) // handle the cancellation (possibly due to an exception) else // do something with the result } });
注意:如果输入的future在不同的线程上完成,此方法返回的未来将在最后一个future完成的线程中完成。因此,附在whenAll()
返回的未来上的延续不能总是假设要在哪个线程上运行。如果您想控制延续要在哪个线程上调用,请使用带参数上下文的.then()
的重载。
此函数是在Qt 6.3中引入的。
[since 6.3]
模版 <typename OutputSequence, typename... Futures> QFuture<OutputSequence> QtFuture::whenAll(Futures &&... futures)
返回一个新的QFuture,当所有包装任意类型的futures完成时,该future将成功。OutputSequence
是一个完成future的序列。其条目类型为std::variant<Futures...>
。对于传递给whenAll()
的每个QFuture<T>
,在OutputSequence
对应位置的条目将是一个包含其完成状态的QFuture<T>
的std::variant
。如果未指定OutputSequence
的类型,则结果future将返回在包含std::variant<Futures...>
的QList中。例如
QFuture<int> intFuture = ...; QFuture<QString> stringFuture = ...; QFuture<void> voidFuture = ...; using FuturesVariant = std::variant<QFuture<int>, QFuture<QString>, QFuture<void>>; // whenAll has type QFuture<QList<FuturesVariant>> auto whenAll = QtFuture::whenAll(intFuture, stringFuture, voidFuture); // whenAllVector has type QFuture<std::vector<FuturesVariant>> auto whenAllVector = QtFuture::whenAll<std::vector<FuturesVariant>>(intFuture, stringFuture, voidFuture);
注意:输出序列应该支持随机访问和resize()
操作。
返回的未来总是在所有指定的future完成后才成功完成。无论这些future中的哪个完成时出错或被取消,都没有关系。您可以在whenAll()
返回的未来之后使用.then()
来处理已完成的future。
QFuture<int> intFuture = ...; QFuture<QString> stringFuture = ...; QFuture<void> voidFuture = ...; using FuturesVariant = std::variant<QFuture<int>, QFuture<QString>, QFuture<void>>; QtFuture::whenAll(intFuture, stringFuture, voidFuture) .then([](const QList<FuturesVariant> &results) { ... for (auto result : results) { // assuming handleResult() is overloaded based on the QFuture type std::visit([](auto &&future) { handleResult(future); }, result); } ... });
注意:如果输入的future在不同的线程上完成,此方法返回的未来将在最后一个future完成的线程中完成。因此,附在whenAll()
返回的未来上的延续不能总是假设要在哪个线程上运行。如果您想控制延续要在哪个线程上调用,请使用带参数上下文的.then()
的重载。
此函数是在Qt 6.3中引入的。
[since 6.3]
模版 <typename T, typename InputIt> QFuture<QtFuture::WhenAnyResult<T>> QtFuture::whenAny(InputIt first, InputIt last)
返回一个新的QFuture,该QFuture在任何从first到last的QFuture完成时都成功。 first和last是打包类型T
的QFuture序列的迭代器。返回的QFuture打包一个类型为QtFuture::WhenAnyResult<T>
的值,后者则打包第一个完成的QFuture的索引和本身。如果first等于last,此函数返回一个准备就绪的QFuture
,其QtFuture::WhenAnyResult
中的index
字段为-1
,并且为future
字段构建一个默认的QFuture<T>
。请注意,默认构建的QFuture是在已取消状态的已完成的QFuture。
返回的QFuture总是在指定的一个QFuture完成后的第一次成功完成。无论第一个QFuture是成功完成还是有错误或被取消,都无关紧要。你可以在whenAny()
返回的QFuture成功后使用.then()
来处理结果
QList<QFuture<int>> inputFutures = ...; QtFuture::whenAny(inputFutures.begin(), inputFutures.end()) .then([](const QtFuture::WhenAnyResult<int> &result) { qsizetype index = result.index; QFuture<int> future = result.future; // ... });
注意: 如果输入的QFuture在不同的线程中完成,此方法返回的QFuture将在第一个QFuture完成的线程中完成。因此,附加到whenAny()
返回的QFuture的后续操作不能总是假设它们将在哪个线程上运行。如果你想控制后续操作在哪个线程上调用,请使用带上下文对象的.then()
的重载。
此函数是在Qt 6.3中引入的。
另请参阅 QtFuture::WhenAnyResult。
[自6.3以来]
模板 <typename... Futures> QFuture<std::variant<std::decay_t<Futures>...>> QtFuture::whenAny(Futures &&... futures)
返回一个新的QFuture,当任何futures完成时都成功。 futures可以打包任意类型。返回的QFuture打包一个类型为std::variant<Futures...>
的值,后者则打包从futures中第一个完成的QFuture。你可以使用std::variant::index()来确定在futures序列中哪个QFuture首先完成。
返回的QFuture总是在指定的一个QFuture完成后的第一次成功完成。无论第一个QFuture是成功完成还是有错误或被取消,都无关紧要。你可以在whenAny()
返回的QFuture成功后使用.then()
来处理结果
QFuture<int> intFuture = ...; QFuture<QString> stringFuture = ...; QFuture<void> voidFuture = ...; using FuturesVariant = std::variant<QFuture<int>, QFuture<QString>, QFuture<void>>; QtFuture::whenAny(intFuture, stringFuture, voidFuture).then([](const FuturesVariant &result) { ... // assuming handleResult() is overloaded based on the QFuture type std::visit([](auto &&future) { handleResult(future); }, result); ... });
注意: 如果输入的QFuture在不同的线程中完成,此方法返回的QFuture将在第一个QFuture完成的线程中完成。因此,附加到whenAny()
返回的QFuture的后续操作不能总是假设它们将在哪个线程上运行。如果你想控制后续操作在哪个线程上调用,请使用带上下文对象的.then()
的重载。
此函数是在Qt 6.3中引入的。
© 2024 Qt公司有限公司。本文件包含的文档贡献均为各自所有者的版权。提供的文档受GNU自由文档许可证版本1.3的条款约束,由自由软件基金会发布。Qt及其相关标志是芬兰及全世界其他国家的Qt公司所有和/或注册商标。所有其他商标均为其各自所有者的财产。