From 727f25214e870bc5d947a2f89ada9a4a4bd07365 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Mon, 27 Aug 2012 18:33:55 +0200 Subject: Move QFuture from QtConcurrent to QtCore This class belongs to QThreadPool/QRunnable more than to QtConcurrent, so move to QtCore, where QThreadPool awaits it. Change-Id: Ibf20288a986593bf779453427c2dae8db1e1423a Reviewed-by: Qt Doc Bot Reviewed-by: Thiago Macieira --- src/corelib/thread/qfuture.h | 276 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 276 insertions(+) create mode 100644 src/corelib/thread/qfuture.h (limited to 'src/corelib/thread/qfuture.h') diff --git a/src/corelib/thread/qfuture.h b/src/corelib/thread/qfuture.h new file mode 100644 index 0000000000..8b16f308f2 --- /dev/null +++ b/src/corelib/thread/qfuture.h @@ -0,0 +1,276 @@ +/**************************************************************************** +** +** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/legal +** +** This file is part of the QtCore module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** Commercial License Usage +** Licensees holding valid commercial Qt licenses may use this file in +** accordance with the commercial license agreement provided with the +** Software or, alternatively, in accordance with the terms contained in +** a written agreement between you and Digia. For licensing terms and +** conditions see http://qt.digia.com/licensing. For further information +** use the contact form at http://qt.digia.com/contact-us. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Digia gives you certain additional +** rights. These rights are described in the Digia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU +** General Public License version 3.0 as published by the Free Software +** Foundation and appearing in the file LICENSE.GPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU General Public License version 3.0 requirements will be +** met: http://www.gnu.org/copyleft/gpl.html. +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef QFUTURE_H +#define QFUTURE_H + +#include + +#ifndef QT_NO_QFUTURE + +#include +#include + +QT_BEGIN_HEADER +QT_BEGIN_NAMESPACE + + +template +class QFutureWatcher; +template <> +class QFutureWatcher; + +template +class QFuture +{ +public: + QFuture() + : d(QFutureInterface::canceledResult()) + { } + explicit QFuture(QFutureInterface *p) // internal + : d(*p) + { } + QFuture(const QFuture &other) + : d(other.d) + { } + ~QFuture() + { } + + inline QFuture &operator=(const QFuture &other); + bool operator==(const QFuture &other) const { return (d == other.d); } + bool operator!=(const QFuture &other) const { return (d != other.d); } + + void cancel() { d.cancel(); } + bool isCanceled() const { return d.isCanceled(); } + + void setPaused(bool paused) { d.setPaused(paused); } + bool isPaused() const { return d.isPaused(); } + void pause() { setPaused(true); } + void resume() { setPaused(false); } + void togglePaused() { d.togglePaused(); } + + bool isStarted() const { return d.isStarted(); } + bool isFinished() const { return d.isFinished(); } + bool isRunning() const { return d.isRunning(); } + + int resultCount() const { return d.resultCount(); } + int progressValue() const { return d.progressValue(); } + int progressMinimum() const { return d.progressMinimum(); } + int progressMaximum() const { return d.progressMaximum(); } + QString progressText() const { return d.progressText(); } + void waitForFinished() { d.waitForFinished(); } + + inline T result() const; + inline T resultAt(int index) const; + bool isResultReadyAt(int resultIndex) const { return d.isResultReadyAt(resultIndex); } + + operator T() const { return result(); } + QList results() const { return d.results(); } + + class const_iterator + { + public: + typedef std::bidirectional_iterator_tag iterator_category; + typedef qptrdiff difference_type; + typedef T value_type; + typedef const T *pointer; + typedef const T &reference; + + inline const_iterator() {} + inline const_iterator(QFuture const * const _future, int _index) : future(_future), index(_index) {} + inline const_iterator(const const_iterator &o) : future(o.future), index(o.index) {} + inline const_iterator &operator=(const const_iterator &o) + { future = o.future; index = o.index; return *this; } + inline const T &operator*() const { return future->d.resultReference(index); } + inline const T *operator->() const { return future->d.resultPointer(index); } + + inline bool operator!=(const const_iterator &other) const + { + if (index == -1 && other.index == -1) // comparing end != end? + return false; + if (other.index == -1) + return (future->isRunning() || (index < future->resultCount())); + return (index != other.index); + } + + inline bool operator==(const const_iterator &o) const { return !operator!=(o); } + inline const_iterator &operator++() { ++index; return *this; } + inline const_iterator operator++(int) { const_iterator r = *this; ++index; return r; } + inline const_iterator &operator--() { --index; return *this; } + inline const_iterator operator--(int) { const_iterator r = *this; --index; return r; } + inline const_iterator operator+(int j) const { return const_iterator(future, index + j); } + inline const_iterator operator-(int j) const { return const_iterator(future, index - j); } + inline const_iterator &operator+=(int j) { index += j; return *this; } + inline const_iterator &operator-=(int j) { index -= j; return *this; } + private: + QFuture const * future; + int index; + }; + friend class const_iterator; + typedef const_iterator ConstIterator; + + const_iterator begin() const { return const_iterator(this, 0); } + const_iterator constBegin() const { return const_iterator(this, 0); } + const_iterator end() const { return const_iterator(this, -1); } + const_iterator constEnd() const { return const_iterator(this, -1); } + +private: + friend class QFutureWatcher; + +public: // Warning: the d pointer is not documented and is considered private. + mutable QFutureInterface d; +}; + +template +inline QFuture &QFuture::operator=(const QFuture &other) +{ + d = other.d; + return *this; +} + +template +inline T QFuture::result() const +{ + d.waitForResult(0); + return d.resultReference(0); +} + +template +inline T QFuture::resultAt(int index) const +{ + d.waitForResult(index); + return d.resultReference(index); +} + +template +inline QFuture QFutureInterface::future() +{ + return QFuture(this); +} + +Q_DECLARE_SEQUENTIAL_ITERATOR(Future) + +template <> +class QFuture +{ +public: + QFuture() + : d(QFutureInterface::canceledResult()) + { } + explicit QFuture(QFutureInterfaceBase *p) // internal + : d(*p) + { } + QFuture(const QFuture &other) + : d(other.d) + { } + ~QFuture() + { } + + QFuture &operator=(const QFuture &other); + bool operator==(const QFuture &other) const { return (d == other.d); } + bool operator!=(const QFuture &other) const { return (d != other.d); } + +#if !defined(Q_CC_XLC) + template + QFuture(const QFuture &other) + : d(other.d) + { } + + template + QFuture &operator=(const QFuture &other) + { + d = other.d; + return *this; + } +#endif + + void cancel() { d.cancel(); } + bool isCanceled() const { return d.isCanceled(); } + + void setPaused(bool paused) { d.setPaused(paused); } + bool isPaused() const { return d.isPaused(); } + void pause() { setPaused(true); } + void resume() { setPaused(false); } + void togglePaused() { d.togglePaused(); } + + bool isStarted() const { return d.isStarted(); } + bool isFinished() const { return d.isFinished(); } + bool isRunning() const { return d.isRunning(); } + + int resultCount() const { return d.resultCount(); } + int progressValue() const { return d.progressValue(); } + int progressMinimum() const { return d.progressMinimum(); } + int progressMaximum() const { return d.progressMaximum(); } + QString progressText() const { return d.progressText(); } + void waitForFinished() { d.waitForFinished(); } + +private: + friend class QFutureWatcher; + +#ifdef QFUTURE_TEST +public: +#endif + mutable QFutureInterfaceBase d; +}; + +inline QFuture &QFuture::operator=(const QFuture &other) +{ + d = other.d; + return *this; +} + +inline QFuture QFutureInterface::future() +{ + return QFuture(this); +} + +template +QFuture qToVoidFuture(const QFuture &future) +{ + return QFuture(future.d); +} + +QT_END_NAMESPACE +QT_END_HEADER + +#endif // QT_NO_QFUTURE + +#endif // QFUTURE_H -- cgit v1.2.3