summaryrefslogtreecommitdiffstats
path: root/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp')
-rw-r--r--tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp199
1 files changed, 149 insertions, 50 deletions
diff --git a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp
index cc4454fbd4..6a92663bc4 100644
--- a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp
+++ b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp
@@ -1,30 +1,5 @@
-/****************************************************************************
-**
-** Copyright (C) 2016 The Qt Company Ltd.
-** Contact: https://www.qt.io/licensing/
-**
-** This file is part of the test suite of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:GPL-EXCEPT$
-** 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 The Qt Company. For licensing terms
-** and conditions see https://www.qt.io/terms-conditions. For further
-** information use the contact form at https://www.qt.io/contact-us.
-**
-** GNU General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU
-** General Public License version 3 as published by the Free Software
-** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
-** included in the packaging of this file. Please review the following
-** information to ensure the GNU General Public License requirements will
-** be met: https://www.gnu.org/licenses/gpl-3.0.html.
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
+// Copyright (C) 2016 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
#include <QtTest/QTest>
#include <QVarLengthArray>
@@ -32,6 +7,8 @@
#include <qscopeguard.h>
#include <qscopedvaluerollback.h>
+#include <algorithm>
+#include <q20iterator.h>
#include <memory>
struct Tracker
@@ -65,13 +42,31 @@ public:
{ return !operator==(lhs, rhs); }
};
+class NonCopyable
+{
+ Q_DISABLE_COPY(NonCopyable)
+ int n;
+public:
+ NonCopyable() : n(0) {}
+ explicit NonCopyable(int n) : n(n) {}
+
+ friend bool operator==(const NonCopyable &lhs, const NonCopyable &rhs) noexcept
+ { return lhs.n == rhs.n; }
+ friend bool operator!=(const NonCopyable &lhs, const NonCopyable &rhs) noexcept
+ { return !operator==(lhs, rhs); }
+};
+
class tst_QVarLengthArray : public QObject
{
Q_OBJECT
private slots:
void defaultConstructor_int() { defaultConstructor<int>(); }
void defaultConstructor_QString() { defaultConstructor<QString>(); }
+ void sizeConstructor_int() { sizeConstructor<int>(); }
+ void sizeConstructor_QString() { sizeConstructor<QString>(); }
+ void sizeConstructor_NonCopyable() { sizeConstructor<NonCopyable>(); }
void append();
+ void preallocatedSize();
#if QT_DEPRECATED_SINCE(6, 3)
void prepend();
#endif
@@ -117,9 +112,13 @@ private slots:
void remove();
void erase();
+ // special cases:
+ void copesWithCopyabilityOfMoveOnlyVector(); // QTBUG-109745
private:
template <typename T>
void defaultConstructor();
+ template <typename T>
+ void sizeConstructor();
template <qsizetype N, typename T>
void move(T t1, T t2);
template <qsizetype N>
@@ -149,6 +148,31 @@ void tst_QVarLengthArray::defaultConstructor()
}
}
+template <typename T>
+void tst_QVarLengthArray::sizeConstructor()
+{
+ {
+ QVarLengthArray<T, 123> vla(0);
+ QCOMPARE(vla.size(), 0);
+ QVERIFY(vla.empty());
+ QVERIFY(vla.isEmpty());
+ QCOMPARE(vla.begin(), vla.end());
+ QCOMPARE(vla.capacity(), 123);
+ }
+ {
+ QVarLengthArray<T, 124> vla(124);
+ QCOMPARE(vla.size(), 124);
+ QVERIFY(!vla.empty());
+ QCOMPARE(vla.capacity(), 124);
+ }
+ {
+ QVarLengthArray<T, 124> vla(125);
+ QCOMPARE(vla.size(), 125);
+ QVERIFY(!vla.empty());
+ QCOMPARE_GE(vla.capacity(), 125);
+ }
+}
+
void tst_QVarLengthArray::append()
{
QVarLengthArray<QString, 2> v;
@@ -171,6 +195,15 @@ void tst_QVarLengthArray::append()
v2.append(5);
}
+void tst_QVarLengthArray::preallocatedSize()
+{
+ // The default is 256:
+ static_assert(QVarLengthArray<int>::PreallocatedSize == 256);
+ // Otherwise, whatever was given as template argument:
+ static_assert(QVarLengthArray<int, 42>::PreallocatedSize == 42);
+ static_assert(QVarLengthArray<int, 1'000'000>::PreallocatedSize == 1'000'000);
+}
+
#if QT_DEPRECATED_SINCE(6, 3)
QT_WARNING_PUSH
QT_WARNING_DISABLE_DEPRECATED
@@ -409,6 +442,17 @@ void tst_QVarLengthArray::appendCausingRealloc()
QVarLengthArray<float, 1> d(1);
for (int i=0; i<30; i++)
d.append(i);
+
+ // Regression test for QTBUG-110412:
+ constexpr qsizetype InitialCapacity = 10;
+ QVarLengthArray<float, InitialCapacity> d2(InitialCapacity);
+ std::iota(d2.begin(), d2.end(), 0.0f);
+ QCOMPARE_EQ(d2.size(), d2.capacity()); // by construction
+ float floats[1000];
+ std::iota(std::begin(floats), std::end(floats), InitialCapacity + 0.0f);
+ d2.append(floats, q20::ssize(floats));
+ QCOMPARE_EQ(d2.size(), q20::ssize(floats) + InitialCapacity);
+ QCOMPARE_GE(d2.capacity(), d2.size());
}
void tst_QVarLengthArray::appendIsStronglyExceptionSafe()
@@ -600,6 +644,12 @@ struct MyBase
bool hasMoved() const { return !wasConstructedAt(this); }
protected:
+ void swap(MyBase &other) {
+ using std::swap;
+ swap(data, other.data);
+ swap(isCopy, other.isCopy);
+ }
+
MyBase(const MyBase *data, bool isCopy)
: data(data), isCopy(isCopy) {}
@@ -674,6 +724,14 @@ struct MyMovable
return *this;
}
+ void swap(MyMovable &other) noexcept
+ {
+ MyBase::swap(other);
+ std::swap(i, other.i);
+ }
+
+ friend void swap(MyMovable &lhs, MyMovable &rhs) noexcept { lhs.swap(rhs); }
+
bool operator==(const MyMovable &other) const
{
return i == other.i;
@@ -689,6 +747,15 @@ struct MyComplex
{
return i == other.i;
}
+
+ void swap(MyComplex &other) noexcept
+ {
+ MyBase::swap(other);
+ std::swap(i, other.i);
+ }
+
+ friend void swap(MyComplex &lhs, MyComplex &rhs) noexcept { lhs.swap(rhs); }
+
char i;
};
@@ -961,8 +1028,8 @@ void tst_QVarLengthArray::count()
// tests size(), count() and length(), since they're the same thing
{
const QVarLengthArray<int> list;
- QCOMPARE(list.length(), 0);
- QCOMPARE(list.count(), 0);
+ QCOMPARE(list.size(), 0);
+ QCOMPARE(list.size(), 0);
QCOMPARE(list.size(), 0);
QVERIFY(list.isEmpty());
}
@@ -970,8 +1037,8 @@ void tst_QVarLengthArray::count()
{
QVarLengthArray<int> list;
list.append(0);
- QCOMPARE(list.length(), 1);
- QCOMPARE(list.count(), 1);
+ QCOMPARE(list.size(), 1);
+ QCOMPARE(list.size(), 1);
QCOMPARE(list.size(), 1);
QVERIFY(!list.isEmpty());
}
@@ -980,8 +1047,8 @@ void tst_QVarLengthArray::count()
QVarLengthArray<int> list;
list.append(0);
list.append(1);
- QCOMPARE(list.length(), 2);
- QCOMPARE(list.count(), 2);
+ QCOMPARE(list.size(), 2);
+ QCOMPARE(list.size(), 2);
QCOMPARE(list.size(), 2);
QVERIFY(!list.isEmpty());
}
@@ -991,8 +1058,8 @@ void tst_QVarLengthArray::count()
list.append(0);
list.append(0);
list.append(0);
- QCOMPARE(list.length(), 3);
- QCOMPARE(list.count(), 3);
+ QCOMPARE(list.size(), 3);
+ QCOMPARE(list.size(), 3);
QCOMPARE(list.size(), 3);
QVERIFY(!list.isEmpty());
}
@@ -1003,23 +1070,23 @@ void tst_QVarLengthArray::count()
list.append(0);
list.append(0);
list.append(0);
- QCOMPARE(list.length(), 3);
- QCOMPARE(list.count(), 3);
+ QCOMPARE(list.size(), 3);
+ QCOMPARE(list.size(), 3);
QCOMPARE(list.size(), 3);
QVERIFY(!list.isEmpty());
list.removeLast();
- QCOMPARE(list.length(), 2);
- QCOMPARE(list.count(), 2);
+ QCOMPARE(list.size(), 2);
+ QCOMPARE(list.size(), 2);
QCOMPARE(list.size(), 2);
QVERIFY(!list.isEmpty());
list.removeLast();
- QCOMPARE(list.length(), 1);
- QCOMPARE(list.count(), 1);
+ QCOMPARE(list.size(), 1);
+ QCOMPARE(list.size(), 1);
QCOMPARE(list.size(), 1);
QVERIFY(!list.isEmpty());
list.removeLast();
- QCOMPARE(list.length(), 0);
- QCOMPARE(list.count(), 0);
+ QCOMPARE(list.size(), 0);
+ QCOMPARE(list.size(), 0);
QCOMPARE(list.size(), 0);
QVERIFY(list.isEmpty());
}
@@ -1058,16 +1125,16 @@ void tst_QVarLengthArray::first()
QCOMPARE(list.first(), 27);
list.append(1987);
QCOMPARE(list.first(), 27);
- QCOMPARE(list.length(), 3);
+ QCOMPARE(list.size(), 3);
// remove some, make sure it stays sane
list.removeLast();
QCOMPARE(list.first(), 27);
- QCOMPARE(list.length(), 2);
+ QCOMPARE(list.size(), 2);
list.removeLast();
QCOMPARE(list.first(), 27);
- QCOMPARE(list.length(), 1);
+ QCOMPARE(list.size(), 1);
}
void tst_QVarLengthArray::last()
@@ -1080,16 +1147,16 @@ void tst_QVarLengthArray::last()
QCOMPARE(list.last(), 4);
list.append(1987);
QCOMPARE(list.last(), 1987);
- QCOMPARE(list.length(), 3);
+ QCOMPARE(list.size(), 3);
// remove some, make sure it stays sane
list.removeLast();
QCOMPARE(list.last(), 4);
- QCOMPARE(list.length(), 2);
+ QCOMPARE(list.size(), 2);
list.removeLast();
QCOMPARE(list.last(), 27);
- QCOMPARE(list.length(), 1);
+ QCOMPARE(list.size(), 1);
}
void tst_QVarLengthArray::squeeze()
@@ -1133,7 +1200,7 @@ void tst_QVarLengthArray::operators()
// +=: not provided, emulate
//myvla += myvlatwo;
- for (const QString &s : qAsConst(myvlatwo))
+ for (const QString &s : std::as_const(myvlatwo))
myvla.push_back(s);
QCOMPARE(myvla, combined);
@@ -1321,6 +1388,17 @@ void tst_QVarLengthArray::insertMove()
QCOMPARE(MyBase::copyCount, 0);
{
+ MyMovable m1, m2;
+ QCOMPARE(MyBase::liveCount, 2);
+ QCOMPARE(MyBase::copyCount, 0);
+ using std::swap;
+ swap(m1, m2);
+ QCOMPARE(MyBase::liveCount, 2);
+ QCOMPARE(MyBase::movedCount, 0);
+ QCOMPARE(MyBase::copyCount, 0);
+ }
+
+ {
QVarLengthArray<MyMovable, 6> vec;
MyMovable m1;
MyMovable m2;
@@ -1665,5 +1743,26 @@ void tst_QVarLengthArray::erase()
QCOMPARE(arr, QVarLengthArray<QString>({ "val0" }));
}
+void tst_QVarLengthArray::copesWithCopyabilityOfMoveOnlyVector()
+{
+ // std::vector<move-only-type> is_copyable
+ // (https://quuxplusone.github.io/blog/2020/02/05/vector-is-copyable-except-when-its-not/)
+
+ QVarLengthArray<std::vector<std::unique_ptr<int>>, 2> vla;
+ vla.emplace_back(42);
+ vla.emplace_back(43);
+ vla.emplace_back(44); // goes to the heap
+ QCOMPARE_EQ(vla.size(), 3);
+ QCOMPARE_EQ(vla.front().size(), 42U);
+ QCOMPARE_EQ(vla.front().front(), nullptr);
+ QCOMPARE_EQ(vla.back().size(), 44U);
+
+ auto moved = std::move(vla);
+ QCOMPARE_EQ(moved.size(), 3);
+ QCOMPARE_EQ(moved.front().size(), 42U);
+ QCOMPARE_EQ(moved.front().front(), nullptr);
+ QCOMPARE_EQ(moved.back().size(), 44U);
+}
+
QTEST_APPLESS_MAIN(tst_QVarLengthArray)
#include "tst_qvarlengtharray.moc"