diff --git a/src/corelib/tools/qlist.h b/src/corelib/tools/qlist.h index fe8a1407e2..6643288bd5 100644 --- a/src/corelib/tools/qlist.h +++ b/src/corelib/tools/qlist.h @@ -118,6 +118,11 @@ struct Q_CORE_EXPORT QListData { inline void **end() const Q_DECL_NOTHROW { return d->array + d->end; } }; +namespace QtPrivate { + template int indexOf(const QList &list, const U &u, int from); + template int lastIndexOf(const QList &list, const U &u, int from); +} + template class QList #ifndef Q_QDOC @@ -136,6 +141,8 @@ public: QListData::InlineWithPaddingLayout >::type>::type {}; private: + template friend int QtPrivate::indexOf(const QList &list, const U &u, int from); + template friend int QtPrivate::lastIndexOf(const QList &list, const U &u, int from); struct Node { void *v; #if defined(Q_CC_BOR) Q_INLINE_TEMPLATE T &t(); @@ -975,35 +982,57 @@ inline void QList::append(const QList &t) template Q_OUTOFLINE_TEMPLATE int QList::indexOf(const T &t, int from) const { + return QtPrivate::indexOf(*this, t, from); +} + +namespace QtPrivate +{ +template +int indexOf(const QList &list, const U &u, int from) +{ + typedef typename QList::Node Node; + if (from < 0) - from = qMax(from + p.size(), 0); - if (from < p.size()) { - Node *n = reinterpret_cast(p.at(from -1)); - Node *e = reinterpret_cast(p.end()); + from = qMax(from + list.p.size(), 0); + if (from < list.p.size()) { + Node *n = reinterpret_cast(list.p.at(from -1)); + Node *e = reinterpret_cast(list.p.end()); while (++n != e) - if (n->t() == t) - return int(n - reinterpret_cast(p.begin())); + if (n->t() == u) + return int(n - reinterpret_cast(list.p.begin())); } return -1; } +} template Q_OUTOFLINE_TEMPLATE int QList::lastIndexOf(const T &t, int from) const { + return QtPrivate::lastIndexOf(*this, t, from); +} + +namespace QtPrivate +{ +template +int lastIndexOf(const QList &list, const U &u, int from) +{ + typedef typename QList::Node Node; + if (from < 0) - from += p.size(); - else if (from >= p.size()) - from = p.size()-1; + from += list.p.size(); + else if (from >= list.p.size()) + from = list.p.size()-1; if (from >= 0) { - Node *b = reinterpret_cast(p.begin()); - Node *n = reinterpret_cast(p.at(from + 1)); + Node *b = reinterpret_cast(list.p.begin()); + Node *n = reinterpret_cast(list.p.at(from + 1)); while (n-- != b) { - if (n->t() == t) + if (n->t() == u) return n - b; } } return -1; } +} template Q_OUTOFLINE_TEMPLATE bool QList::contains(const T &t) const diff --git a/src/corelib/tools/qstringlist.cpp b/src/corelib/tools/qstringlist.cpp index ec6de08805..cc6eaf8ad2 100644 --- a/src/corelib/tools/qstringlist.cpp +++ b/src/corelib/tools/qstringlist.cpp @@ -376,6 +376,56 @@ bool QtPrivate::QStringList_contains(const QStringList *that, QLatin1String str, return stringList_contains(*that, str, cs); } +/*! + \fn bool QStringList::indexOf(QStringView str, int from) const + \overload + \since 5.13 + + Returns the index position of the first occurrence of \a str in + the list, searching forward from index position \a from. Returns + -1 if no item matched. + + \sa lastIndexOf(), contains() + */ + +/*! + \fn bool QStringList::indexOf(QLatin1String str, int from) const + \overload + \since 5.13 + + Returns the index position of the first occurrence of \a str in + the list, searching forward from index position \a from. Returns + -1 if no item matched. + + \sa lastIndexOf(), contains() + */ + +/*! + \fn bool QStringList::lastIndexOf(QStringView str, int from) const + \overload + \since 5.13 + + Returns the index position of the last occurrence of \a str in + the list, searching backward from index position \a from. If \a + from is -1 (the default), the search starts at the last item. + Returns -1 if no item matched. + + \sa indexOf(), contains() + */ + +/*! + \fn bool QStringList::lastIndexOf(QLatin1String str, int from) const + \overload + \since 5.13 + + Returns the index position of the last occurrence of \a str in + the list, searching backward from index position \a from. If \a + from is -1 (the default), the search starts at the last item. + Returns -1 if no item matched. + + \sa indexOf(), contains() + */ + #ifndef QT_NO_REGEXP /*! \fn QStringList QStringList::filter(const QRegExp &rx) const diff --git a/src/corelib/tools/qstringlist.h b/src/corelib/tools/qstringlist.h index 10cbad04d6..b6c48488df 100644 --- a/src/corelib/tools/qstringlist.h +++ b/src/corelib/tools/qstringlist.h @@ -132,6 +132,12 @@ public: inline QStringList &operator<<(const QList &l) { *this += l; return *this; } + inline int indexOf(QStringView str, int from = 0) const; + inline int indexOf(QLatin1String str, int from = 0) const; + + inline int lastIndexOf(QStringView str, int from = -1) const; + inline int lastIndexOf(QLatin1String str, int from = -1) const; + #ifndef QT_NO_REGEXP inline int indexOf(const QRegExp &rx, int from = 0) const; inline int lastIndexOf(const QRegExp &rx, int from = -1) const; @@ -249,6 +255,26 @@ inline QStringList operator+(const QList &one, const QStringList &other return n; } +inline int QStringList::indexOf(QStringView string, int from) const +{ + return QtPrivate::indexOf(*this, string, from); +} + +inline int QStringList::indexOf(QLatin1String string, int from) const +{ + return QtPrivate::indexOf(*this, string, from); +} + +inline int QStringList::lastIndexOf(QStringView string, int from) const +{ + return QtPrivate::lastIndexOf(*this, string, from); +} + +inline int QStringList::lastIndexOf(QLatin1String string, int from) const +{ + return QtPrivate::lastIndexOf(*this, string, from); +} + #ifndef QT_NO_REGEXP inline QStringList &QListSpecialMethods::replaceInStrings(const QRegExp &rx, const QString &after) { diff --git a/tests/auto/corelib/tools/qstringlist/tst_qstringlist.cpp b/tests/auto/corelib/tools/qstringlist/tst_qstringlist.cpp index a3aec4c299..42bdf62a93 100644 --- a/tests/auto/corelib/tools/qstringlist/tst_qstringlist.cpp +++ b/tests/auto/corelib/tools/qstringlist/tst_qstringlist.cpp @@ -43,7 +43,9 @@ private slots: void removeDuplicates(); void removeDuplicates_data(); void contains(); + void indexOf_data(); void indexOf(); + void lastIndexOf_data(); void lastIndexOf(); void indexOf_regExp(); @@ -141,20 +143,52 @@ void tst_QStringList::lastIndexOf_regExp() } +void tst_QStringList::indexOf_data() +{ + QTest::addColumn("search"); + QTest::addColumn("from"); + QTest::addColumn("expectedResult"); + + QTest::newRow("harald") << "harald" << 0 << 0; + QTest::newRow("trond") << "trond" << 0 << 1; + QTest::newRow("vohi") << "vohi" << 0 << 2; + QTest::newRow("harald-1") << "harald" << 1 << 3; + + QTest::newRow("hans") << "hans" << 0 << -1; + QTest::newRow("trond-1") << "trond" << 2 << -1; + QTest::newRow("harald-2") << "harald" << -1 << 3; + QTest::newRow("vohi-1") << "vohi" << -3 << 2; +} + void tst_QStringList::indexOf() { QStringList list; list << "harald" << "trond" << "vohi" << "harald"; - QCOMPARE(list.indexOf("harald"), 0); - QCOMPARE(list.indexOf("trond"), 1); - QCOMPARE(list.indexOf("vohi"), 2); - QCOMPARE(list.indexOf("harald", 1), 3); + QFETCH(QString, search); + QFETCH(int, from); + QFETCH(int, expectedResult); - QCOMPARE(list.indexOf("hans"), -1); - QCOMPARE(list.indexOf("trond", 2), -1); - QCOMPARE(list.indexOf("harald", -1), 3); - QCOMPARE(list.indexOf("vohi", -3), 2); + QCOMPARE(list.indexOf(search, from), expectedResult); + QCOMPARE(list.indexOf(QStringView(search), from), expectedResult); + QCOMPARE(list.indexOf(QLatin1String(search.toLatin1()), from), expectedResult); +} + +void tst_QStringList::lastIndexOf_data() +{ + QTest::addColumn("search"); + QTest::addColumn("from"); + QTest::addColumn("expectedResult"); + + QTest::newRow("harald") << "harald" << -1 << 3; + QTest::newRow("trond") << "trond" << -1 << 1; + QTest::newRow("vohi") << "vohi" << -1 << 2; + QTest::newRow("harald-1") << "harald" << 2 << 0; + + QTest::newRow("hans") << "hans" << -1 << -1; + QTest::newRow("vohi-1") << "vohi" << 1 << -1; + QTest::newRow("vohi-2") << "vohi" << -1 << 2; + QTest::newRow("vohi-3") << "vohi" << -3 << -1; } void tst_QStringList::lastIndexOf() @@ -162,15 +196,13 @@ void tst_QStringList::lastIndexOf() QStringList list; list << "harald" << "trond" << "vohi" << "harald"; - QCOMPARE(list.lastIndexOf("harald"), 3); - QCOMPARE(list.lastIndexOf("trond"), 1); - QCOMPARE(list.lastIndexOf("vohi"), 2); - QCOMPARE(list.lastIndexOf("harald", 2), 0); + QFETCH(QString, search); + QFETCH(int, from); + QFETCH(int, expectedResult); - QCOMPARE(list.lastIndexOf("hans"), -1); - QCOMPARE(list.lastIndexOf("vohi", 1), -1); - QCOMPARE(list.lastIndexOf("vohi", -1), 2); - QCOMPARE(list.lastIndexOf("vohi", -3), -1); + QCOMPARE(list.lastIndexOf(search, from), expectedResult); + QCOMPARE(list.lastIndexOf(QStringView(search), from), expectedResult); + QCOMPARE(list.lastIndexOf(QLatin1String(search.toLatin1()), from), expectedResult); } void tst_QStringList::filter()