[libc-commits] [libc] [libc][FixedVector] Add more helper methods (PR #94278)
via libc-commits
libc-commits at lists.llvm.org
Mon Jun 3 13:27:48 PDT 2024
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-libc
Author: None (PiJoules)
<details>
<summary>Changes</summary>
This adds:
- A ctor accepting a start and end iterator
- A ctor accepting a count and const T&
- size()
- subscript operators
- begin() and end() iterators
---
Full diff: https://github.com/llvm/llvm-project/pull/94278.diff
3 Files Affected:
- (modified) libc/src/__support/fixedvector.h (+20)
- (modified) libc/test/src/__support/CMakeLists.txt (+1)
- (modified) libc/test/src/__support/fixedvector_test.cpp (+35)
``````````diff
diff --git a/libc/src/__support/fixedvector.h b/libc/src/__support/fixedvector.h
index 81747ee10067c..b06321887e7a1 100644
--- a/libc/src/__support/fixedvector.h
+++ b/libc/src/__support/fixedvector.h
@@ -24,6 +24,16 @@ template <typename T, size_t CAPACITY> class FixedVector {
public:
constexpr FixedVector() = default;
+ template <typename It> constexpr FixedVector(It begin, It end) {
+ for (; begin != end; ++begin)
+ push_back(*begin);
+ }
+
+ constexpr FixedVector(size_t count, const T &value) {
+ for (size_t i = 0; i < count; ++i)
+ push_back(value);
+ }
+
bool push_back(const T &obj) {
if (item_count == CAPACITY)
return false;
@@ -43,8 +53,14 @@ template <typename T, size_t CAPACITY> class FixedVector {
return true;
}
+ T &operator[](size_t idx) { return store[idx]; }
+
+ const T &operator[](size_t idx) const { return store[idx]; }
+
bool empty() const { return item_count == 0; }
+ size_t size() const { return item_count; }
+
// Empties the store for all practical purposes.
void reset() { item_count = 0; }
@@ -63,6 +79,10 @@ template <typename T, size_t CAPACITY> class FixedVector {
return reverse_iterator{&store[item_count]};
}
LIBC_INLINE constexpr reverse_iterator rend() { return store.rend(); }
+
+ using iterator = typename cpp::array<T, CAPACITY>::iterator;
+ LIBC_INLINE constexpr iterator begin() { return store.begin(); }
+ LIBC_INLINE constexpr iterator end() { return iterator{&store[item_count]}; }
};
} // namespace LIBC_NAMESPACE
diff --git a/libc/test/src/__support/CMakeLists.txt b/libc/test/src/__support/CMakeLists.txt
index 663aa2bb82cae..936cfe4e2a20c 100644
--- a/libc/test/src/__support/CMakeLists.txt
+++ b/libc/test/src/__support/CMakeLists.txt
@@ -132,6 +132,7 @@ add_libc_test(
SRCS
fixedvector_test.cpp
DEPENDS
+ libc.src.__support.CPP.array
libc.src.__support.fixedvector
)
diff --git a/libc/test/src/__support/fixedvector_test.cpp b/libc/test/src/__support/fixedvector_test.cpp
index 4e92081321de7..c61b9ca815643 100644
--- a/libc/test/src/__support/fixedvector_test.cpp
+++ b/libc/test/src/__support/fixedvector_test.cpp
@@ -6,6 +6,7 @@
//
//===----------------------------------------------------------------------===//
+#include "src/__support/CPP/array.h"
#include "src/__support/fixedvector.h"
#include "test/UnitTest/Test.h"
@@ -59,3 +60,37 @@ TEST(LlvmLibcFixedVectorTest, Iteration) {
for (auto it = v.rbegin(), e = v.rend(); it != e; ++it)
ASSERT_GT(*it, -1);
}
+
+TEST(LlvmLibcFixedVectorTest, ConstructionFromIterators) {
+ LIBC_NAMESPACE::cpp::array<int, 4> arr{1, 2, 3, 4};
+ LIBC_NAMESPACE::FixedVector<int, 5> vec(arr.begin(), arr.end());
+ ASSERT_EQ(vec.size(), arr.size());
+ for (size_t i = 0; i < arr.size(); ++i)
+ ASSERT_EQ(vec[i], arr[i]);
+}
+
+TEST(LlvmLibcFixedVectorTest, ConstructionFromCountAndValue) {
+ constexpr int kVal = 10;
+ // TODO: If the first argument here were just `4`, then we'd have no way to
+ // disambiguate between the FixedVector ctor that uses iterators vs the one
+ // taking a count and `cosnt T &`. Using `4` would result in a compile error.
+ // Formally, we can ensure the count + reference ctor is used if we gate the
+ // iterator ctor on checking if the type has the `input_iterator_tag` via
+ // iterator_traits, but we'd have to plumb that through which can be done
+ // separately. Note the snafu we hit here only happens because we happen to
+ // test with containters using integral types.
+ LIBC_NAMESPACE::FixedVector<int, 5> vec(size_t(4), kVal);
+ ASSERT_EQ(vec.size(), size_t(4));
+ for (size_t i = 0; i < vec.size(); ++i)
+ ASSERT_EQ(vec[i], kVal);
+}
+
+TEST(LlvmLibcFixedVectorTest, ForwardIteration) {
+ LIBC_NAMESPACE::cpp::array<int, 4> arr{1, 2, 3, 4};
+ LIBC_NAMESPACE::FixedVector<int, 5> vec(arr.begin(), arr.end());
+ ASSERT_EQ(vec.size(), arr.size());
+ for (auto it = vec.begin(); it != vec.end(); ++it) {
+ auto idx = it - vec.begin();
+ ASSERT_EQ(*it, arr[idx]);
+ }
+}
``````````
</details>
https://github.com/llvm/llvm-project/pull/94278
More information about the libc-commits
mailing list