Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there a standard C++ class for arrays with fixed run-time-determined size?

Tags:

c++

arrays

c++20

I need a container with run-time known size with no need to resizing. std::unique_ptr<T[]> would be a useful, but there is no encapsulated size member. In the same time std::array is for compile type size only. Hence I need some combination of these classes with no/minimal overhead.

Is there a standard class for my needs, maybe something in upcoming C++20?

like image 929
αλεχολυτ Avatar asked Mar 27 '19 11:03

αλεχολυτ


People also ask

Do arrays have fixed size in C?

Arrays a kind of data structure that can store a fixed-size sequential collection of elements of the same type. An array is used to store a collection of data, but it is often more useful to think of an array as a collection of variables of the same type.

Can we get size of array at run time?

No. In an array declaration, the size must be known at compile time. You can�t specify a size that�s known only at runtime.

Can we change size of array at runtime in C?

Size of Variable Length Arrays can be set at runtime, but we could not change their size once set. Unlike static arrays, Dynamic arrays in C are allocated on the heap and we could change their size in runtime.

Does an array have a fixed size?

Arrays are fixed size. Once we initialize the array with some int value as its size, it can't change.


2 Answers

Allocate the memory using an std::unique_ptr<T[]> like you suggested, but to use it - construct an std::span (in C++20; gsl::span before C++20) from the raw pointer and the number of elements, and pass the span around (by value; spans are reference-types, sort of). The span will give you all the bells and whistles of a container: size, iterators, ranged-for, the works.

#include <span>
// or:
// #include <gsl/span>

int main() {

    // ... etc. ...

    {
        size_t size = 10e5;
        auto uptr { std::make_unique<double[]>(size) };
        std::span<int> my_span { uptr.get(), size };
        do_stuff_with_the_doubles(my_span);
    }

    // ... etc. ...
}

For more information about spans, see:

What is a "span" and when should I use one?

like image 79
einpoklum Avatar answered Nov 07 '22 20:11

einpoklum


Use std::vector. If you want to remove the possibility of changing it's size, wrap it.

template <typename T>
single_allocation_vector : private std::vector<T>, public gsl::span<T>
{
    single_allocation_vector(size_t n, T t = {}) : vector(n, t), span(vector::data(), n) {}
    // other constructors to taste
};
like image 44
Caleth Avatar answered Nov 07 '22 20:11

Caleth