diff --git a/src/libs/utils/sizedarray.h b/src/libs/utils/sizedarray.h new file mode 100644 index 00000000000..1f7efef315a --- /dev/null +++ b/src/libs/utils/sizedarray.h @@ -0,0 +1,117 @@ +/**************************************************************************** +** +** Copyright (C) 2016 The Qt Company Ltd. +** Contact: https://www.qt.io/licensing/ +** +** This file is part of Qt Creator. +** +** 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. +** +****************************************************************************/ + +#pragma once + +#include +#include + +#pragma push_macro("constexpr") +#ifndef __cpp_constexpr +#define constexpr +#endif + +namespace Utils { + +template +class SizedArray : public std::array +{ +public: + using size_type = std::uint8_t; + using reference = typename std::array::reference; + using const_reference = typename std::array::const_reference; + using iterator = typename std::array::iterator; + using const_iterator = typename std::array::const_iterator; + using reverse_iterator = typename std::array::reverse_iterator; + using const_reverse_iterator = typename std::array::const_reverse_iterator; + using value_type = typename std::array::value_type; + using pointer = typename std::array::pointer; + using difference_type = typename std::array::difference_type; + + using std::array::operator[]; + using std::array::begin; + using std::array::cbegin; + using std::array::rend; + using std::array::crend; + + constexpr size_type size() const + { + return m_size; + } + + void push_back(const T &value) + { + operator[](m_size) = value; + + ++m_size; + } + + constexpr const_reference back() const + { + return operator[](m_size - 1); + } + + iterator end() + { + return std::next(begin(), m_size); + } + + const_iterator end() const + { + return std::next(begin(), m_size); + } + + const_iterator cend() const + { + return std::next(cbegin(), m_size); + } + + reverse_iterator rbegin() + { + return std::prev(rend(), m_size); + } + + const_reverse_iterator rbegin() const + { + return std::prev(rend(), m_size); + } + + const_reverse_iterator crbegin() const + { + return std::prev(crend(), m_size); + } + + bool empty() const + { + return m_size == 0; + } + +private: + std::uint8_t m_size = 0; +}; + +} // namespace Utils + +#pragma pop_macro("constexpr") diff --git a/src/libs/utils/utils-lib.pri b/src/libs/utils/utils-lib.pri index f100af97d5e..c952b2ebef3 100644 --- a/src/libs/utils/utils-lib.pri +++ b/src/libs/utils/utils-lib.pri @@ -217,7 +217,8 @@ HEADERS += \ $$PWD/smallstringliteral.h \ $$PWD/smallstringmemory.h \ $$PWD/smallstringvector.h \ - $$PWD/smallstringlayout.h + $$PWD/smallstringlayout.h \ + $$PWD/sizedarray.h FORMS += $$PWD/filewizardpage.ui \ $$PWD/projectintropage.ui \ diff --git a/src/libs/utils/utils.qbs b/src/libs/utils/utils.qbs index 38bf4e8919d..7f69e1a0d80 100644 --- a/src/libs/utils/utils.qbs +++ b/src/libs/utils/utils.qbs @@ -182,6 +182,7 @@ QtcLibrary { "shellcommand.h", "shellcommandpage.cpp", "shellcommandpage.h", + "sizedarray.h", "sleep.cpp", "sleep.h", "smallstring.h", diff --git a/tests/unit/unittest/sizedarraytest.cpp b/tests/unit/unittest/sizedarraytest.cpp new file mode 100644 index 00000000000..1af4f45f540 --- /dev/null +++ b/tests/unit/unittest/sizedarraytest.cpp @@ -0,0 +1,150 @@ +/**************************************************************************** +** +** Copyright (C) 2016 The Qt Company Ltd. +** Contact: https://www.qt.io/licensing/ +** +** This file is part of Qt Creator. +** +** 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. +** +****************************************************************************/ + +#include "gtest/gtest.h" +#include "gmock/gmock-matchers.h" +#include "gtest-qt-printing.h" + +#include + +namespace { + +using Utils::SizedArray; + +TEST(SizedArray, EmptySize) +{ + SizedArray array; + + ASSERT_THAT(array.size(), 0); +} + +TEST(SizedArray, IsEmpty) +{ + SizedArray array; + + ASSERT_TRUE(array.empty()); +} + +TEST(SizedArray, IsNotEmpty) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_FALSE(array.empty()); +} + +TEST(SizedArray, SizeOneAfterPushBack) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_THAT(array.size(), 1); +} + +TEST(SizedArray, FirstValueAfterPushBack) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_THAT(array.front(), 'x'); +} + +TEST(SizedArray, LastValueAfterPushBack) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_THAT(array.back(), 'x'); +} + +TEST(SizedArray, EndIteratorIsEqualBeginForEmptyArray) +{ + SizedArray array; + + ASSERT_THAT(array.begin(), array.end()); +} + +TEST(SizedArray, ConstEndIteratorIsEqualBeginForEmptyArray) +{ + const SizedArray array = {}; + + ASSERT_THAT(array.begin(), array.end()); +} + +TEST(SizedArray, EndIteratorIsOneAfterBeginForOneSizedArray) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_THAT(std::next(array.begin(), 1), array.end()); +} + +TEST(SizedArray, CEndIteratorIsOneAfterBeginForOneSizedArray) +{ + SizedArray array = {}; + + array.push_back('x'); + + ASSERT_THAT(std::next(array.cbegin(), 1), array.cend()); +} + +TEST(SizedArray, REndIteratorIsEqualRBeginForEmptyArray) +{ + SizedArray array; + + ASSERT_THAT(array.rbegin(), array.rend()); +} + +TEST(SizedArray, ConstREndIteratorIsEqualRBeginForEmptyArray) +{ + const SizedArray array = {}; + + ASSERT_THAT(array.rbegin(), array.rend()); +} + +TEST(SizedArray, REndIteratorIsOneAfterRBeginForOneSizedArray) +{ + SizedArray array; + + array.push_back('x'); + + ASSERT_THAT(std::next(array.rbegin(), 1), array.rend()); +} + +TEST(SizedArray, ConstREndIteratorIsOneAfterRBeginForOneSizedArray) +{ + SizedArray array = {}; + + array.push_back('x'); + + ASSERT_THAT(std::next(array.crbegin(), 1), array.crend()); +} + +} // anonymous namespace diff --git a/tests/unit/unittest/unittest.pro b/tests/unit/unittest/unittest.pro index 9704c2572c3..577e7fc3592 100644 --- a/tests/unit/unittest/unittest.pro +++ b/tests/unit/unittest/unittest.pro @@ -67,7 +67,8 @@ SOURCES += \ chunksreportedmonitor.cpp \ unsavedfiletest.cpp \ clangisdiagnosticrelatedtolocationtest.cpp \ - smallstringtest.cpp + smallstringtest.cpp \ + sizedarraytest.cpp exists($$GOOGLEBENCHMARK_DIR) { SOURCES += \