привет мне нужно было написать определенный код и у меня есть программа проверяющая этот код, но он не проходит эту проверку тебе нужно мне помочь его исправить
вот мой код:
#pragma once
#include <vector>
#include <algorithm>
#include <cstddef>
#include <utility>

template <typename T>
class FlattenedVector {
    public:
        using iterator_category = std::random_access_iterator_tag;
        using value_type = T;
        using difference_type = std::ptrdiff_t;
        using pointer = T*;
        using reference = T&;

        class Iterator {
            public:
                using iterator_category = std::random_access_iterator_tag;
                using value_type = T;
                using difference_type = std::ptrdiff_t;
                using pointer = T*;
                using reference = T&;

                Iterator(const FlattenedVector<T>* parent, size_t ind)
                    : parent_(parent), ind_(ind) {}
                
                T& operator*() {
                    return const_cast<FlattenedVector<T>*>(parent_)->at(ind_);
                }

                const T& operator*() const {
                    return parent_->at(ind_);
                }

                T* operator->() {
                    return &(**this);
                }

                const T* operator->() const {
                    return &(**this);
                }

                Iterator& operator++() {
                    ++ind_;
                    return *this;
                }

                Iterator operator++(int) {
                    Iterator temp = *this;
                    ++(*this);
                    return temp;;
                }

                Iterator& operator--() {
                    --ind_;
                    return *this;
                }

                Iterator operator--(int) {
                    Iterator temp = *this;
                    --(*this);
                    return temp;;
                }

                Iterator operator+(std::ptrdiff_t n) const {
                    return Iterator(parent_, ind_ + n);
                } 

                friend Iterator operator+(std::ptrdiff_t n, const Iterator& it) {
                    return it + n;
                }

                Iterator& operator+=(std::ptrdiff_t n) {
                    ind_ += n;
                    return *this;
                }

                Iterator operator-(std::ptrdiff_t n) const {
                    return Iterator(parent_, ind_ - n);
                }

                Iterator& operator-=(std::ptrdiff_t n) {
                    ind_ -= n;
                    return *this;
                }

                std::ptrdiff_t operator-(const Iterator& other) const {
                    return static_cast<std::ptrdiff_t>(ind_) - static_cast<std::ptrdiff_t>(other.ind_);
                }

                T& operator[](std::ptrdiff_t n) {
                    return *(*this + n);
                }

                const T& operator[](std::ptrdiff_t n) const {
                    return *(*this + n);
                }

                bool operator<(const Iterator& other) const {
                    return ind_ < other.ind_;
                }

                bool operator>(const Iterator& other) const {
                    return ind_ > other.ind_;
                }

                bool operator<=(const Iterator& other) const {
                    return ind_ <= other.ind_;
                }

                bool operator>=(const Iterator& other) const {
                    return ind_ >= other.ind_;
                }

                bool operator==(const Iterator& other) const {
                    return ind_ == other.ind_;
                }

                bool operator!=(const Iterator& other) const {
                    return ind_ != other.ind_;
                }
            
            private:
                const FlattenedVector<T>* parent_;
                size_t ind_;
            
        };

        FlattenedVector(std::vector<std::vector<T>>& data)
            : data_(&data) {
                prefixsum.reserve(data_->size() + 1);
                prefixsum.push_back(0);
                for (const auto& temp : *data_) {
                    prefixsum.push_back(prefixsum.back() + temp.size());
                }
            }

        FlattenedVector(const std::vector<std::vector<T>>& data)
            : data_(&const_cast<std::vector<std::vector<T>>&>(data)) {
                prefixsum.reserve(data_->size() + 1);
                prefixsum.push_back(0);
                for (const auto& temp : *data_) {
                    prefixsum.push_back(prefixsum.back() + temp.size());
                }
            }
        
        Iterator begin() {
            return Iterator(this,0);
        }

        Iterator end() {
            return Iterator(this, size());
        }

        Iterator begin() const {
            return Iterator(this,0);
        }

        Iterator end() const {
            return Iterator(this, size());
        }

        size_t size() const {
            if (prefixsum.empty()){
                return 0;
            }
            else {
                return prefixsum.back();
            }
        }

        bool empty() const {
            return size() == 0;
        }

        T& at(size_t ind) {
            auto [temp_idx, local_idx] = find_pos(ind);
            return (*data_)[temp_idx][local_idx];
        }

        const T& at(size_t ind) const {
            auto [temp_idx, local_idx] = find_pos(ind);
            return (*data_)[temp_idx][local_idx];
        }

        const T& operator[](size_t ind) const {
            return at(ind);
        }
        
        T& operator[](size_t ind) {
            return at(ind);
        }

    private:
        const std::vector<std::vector<T>>* data_;
        std::vector<size_t> prefixsum;

        std::pair<size_t, size_t> find_pos(size_t ind) const {
            auto it = std::upper_bound(prefixsum.begin(), prefixsum.end(), ind);
            size_t temp_idx = std::distance(prefixsum.begin(), it) - 1;
            size_t local_idx = ind - prefixsum[temp_idx];
            return {temp_idx, local_idx};
        }
};
вот код для проверки:
#include "flatten.h"

#if defined(_LIBCPP_LIST) || defined(_LIBCPP_DEQUE) || defined(_LIBCPP_FORWARD_LIST)
#error "include list or deque forbidden"
#endif

#include <algorithm>
#include <cassert>
#include <chrono>
#include <memory>
#include <random>
#include <string>
#include <vector>

namespace {

    struct TestData {
        int first;
        char second;
        int64_t third;
        std::string fourth;
    };

    std::mt19937 g_random_engine(11);

    template <typename T, typename Generator>
    std::vector<std::vector<T>> GenerateSample(int total_count, int empty_count, Generator generator) {
        assert(total_count >= empty_count);

        std::vector<std::vector<T>> sample(total_count);

        std::uniform_int_distribution<int> size_dist(1, 5);
        for (int i = empty_count; i < total_count; ++i) {
            const int size = size_dist(g_random_engine);
            for (int j = 0; j < size; ++j) {
                sample[i].push_back(generator());
            }
        }

        std::shuffle(sample.begin(), sample.end(), g_random_engine);

        return sample;
    }

    template <typename T>
    std::vector<T> Flatten(const std::vector<std::vector<T>>& vector) {
        std::vector<T> result;

        for (const auto& sub_vector : vector) {
            for (const auto& el : sub_vector) {
                result.push_back(el);
            }
        }

        return result;
    }

}

void TestProperties() {
    {
        assert(sizeof(FlattenedVector<double>) <= 40);
        assert(sizeof(FlattenedVector<TestData>) <= 40);
        assert(sizeof(std::declval<FlattenedVector<TestData>>().begin()) <= 32);
        assert(sizeof(std::declval<FlattenedVector<TestData>>().end()) <= 32);
    }

    {
        auto vector = GenerateSample<int64_t>(10, 3, g_random_engine);
        const auto flattened = Flatten(vector);
        int i = 0;
        for (auto x : FlattenedVector<int64_t>(vector)) {
            assert(x == flattened[i++]);
        }
    }

    {
        auto vector = GenerateSample<int>(100, 10, g_random_engine);
        const auto expected = Flatten(vector);

        FlattenedVector<int> flattened_vector(vector);

        assert(std::distance(flattened_vector.begin(), flattened_vector.end()) == static_cast<ssize_t>(expected.size()));

        auto iter = flattened_vector.begin() + 33;
        assert(((void)[](auto x){ ++x; }(iter), *iter) == *iter);

        const auto it_a = flattened_vector.begin() + 11;
        const auto it_b = flattened_vector.begin() + 42;
        const auto diff = it_b - it_a;

        assert(diff == 42 - 11);

        assert(it_a <= it_b);
        assert(it_b != it_a);
        assert(it_b > it_a);

        assert((it_a + diff) == (diff + it_a));
        assert((it_a + 0) == it_a);
        assert(it_a[diff] == *it_b);

        [diff](auto a, auto b) {
            assert((a += diff) == b);
        }(it_a, it_b);
        [diff](auto a, auto b) {
            assert((b -= diff) == a);
        }(it_a, it_b);
        [diff](auto a) {
            assert(std::addressof(a += diff) == std::addressof(a));
        }(it_a);
        [diff](auto b) {
            assert(std::addressof(b -= diff) == std::addressof(b));
        }(it_b);
        [it_a, diff](auto a) {
            assert((it_a + diff) == (a += diff));
        }(it_a);
        [it_b, diff](auto b) {
            assert((it_b - diff) == (b -= diff));
        }(it_b);
        [diff](auto a, auto b) {
            assert((a + (diff - 1)) == (--b));
        }(it_a, it_b);
    }
}

void TestSimple() {
    std::vector<std::vector<int>> vector = {
        {},
        {0},
        {1, 2, 3, 4, 5, 6, 7},
        {},
        {},
        {8, 9},
        {10},
        {},
        {11},
        {12, 13, 14, 15, 16},
        {17, 18},
        {},
        {19},
        {},
        {20, 21, 22},
        {},
        {},
    };

    FlattenedVector fv(vector);

    auto it = fv.begin();
    assert(it[10] == 10);
    assert(it[0] == 0);
    assert(it[15] == 15);

    assert(*it == 0);
    it += 10;
    assert(*it == 10);
    it -= -3;
    assert(*it == 13);
    it -= 2;
    assert(*it == 11);
    --it;
    assert(*it == 10);
    it += 6;
    assert(*it == 16);
    it += 3;
    assert(*it == 19);
    it += -2;
    assert(*it == 17);
    it -= 9;
    assert(*it == 8);
    it += -8;
    assert(*it == 0);
    it -= -22;
    assert(*it == 22);
}

void TestEmpty() {
    for (auto vector : {std::vector<std::vector<TestData>>{}, std::vector<std::vector<TestData>>{{}, {}}}) {
        FlattenedVector<TestData> fv(vector);
        assert(std::distance(fv.begin(), fv.end()) == 0);
        assert(fv.begin() == fv.end());
        for (auto x : fv) {
            assert(false);
        }
    }
}

void TestModify() {
    {
        auto vector = GenerateSample<char>(100, 10, []() { return 'a' + g_random_engine() % 26; });
        FlattenedVector<char> flattened_vector(vector);

        const auto it = flattened_vector.begin() + 42;
        const char old_value = *it;
        const char new_value = old_value + 1;
        *it = new_value;
        assert(*it == new_value);

        const char value = it[1] == old_value ? old_value : new_value;
        it[1] = value;
        assert(*(it + 1) == value);
    }

    {
        auto vector = GenerateSample<int>(1000, 100, g_random_engine);
        auto expected = Flatten(vector);
        std::sort(expected.begin(), expected.end());

        FlattenedVector<int> flattened_vector(vector);
        std::sort(flattened_vector.begin(), flattened_vector.end());

        assert(Flatten(vector) == expected);
    }
}

void TestStress() {
    auto test = [](std::vector<std::vector<uint64_t>> vector) {
        const auto flattened = Flatten(vector);
        const auto size = flattened.size();

        const auto start_ts = std::chrono::steady_clock::now();

        FlattenedVector<uint64_t> flattened_vector(vector);
        auto flattening_iter = flattened_vector.begin();
        for (int i = 0, pos = 0; i < 100000; ++i) {
            assert(std::distance(flattened_vector.begin(), flattening_iter) == pos);
            int new_pos = 0;
            if (i & 1) {
                std::uniform_int_distribution<int> step_dist(0, size / 100);
                new_pos = step_dist(g_random_engine);
            } else {
                std::uniform_int_distribution<int> step_dist(9 * size / 100, size - 1);
                new_pos = step_dist(g_random_engine);
            }
            flattening_iter += new_pos - pos;
            pos = new_pos;
            assert(flattened[pos] == *flattening_iter);
        }

        const std::chrono::duration<double> elapsed_time = std::chrono::steady_clock::now() - start_ts;
        assert(elapsed_time.count() < 0.5);
    };

    {
        auto vector = GenerateSample<uint64_t>(200000, 184321, g_random_engine);
        test(vector);
    }

    {
        auto vector = GenerateSample<uint64_t>(200000, 1234, g_random_engine);
        test(vector);
    }

    {
        std::vector<std::vector<int>> vector{{1}};
        for (int i = 0; i < 100000; ++i) {
            vector.emplace_back(std::vector<int>{});
        }
        vector.emplace_back(std::vector<int>{2, 1});

        const auto start_ts = std::chrono::steady_clock::now();

        FlattenedVector<int> flattened_vector(vector);
        auto flattening_iter = flattened_vector.begin();
        for (int i = 0; i < 100000; ++i) {
            if (i & 1) {
                --flattening_iter;
                assert(*flattening_iter == 1);
            } else {
                ++flattening_iter;
                assert(*flattening_iter == 2);
            }
        }
        ++flattening_iter;
        ++flattening_iter;
        assert(*flattening_iter == 1);
        --flattening_iter;
        assert(*flattening_iter == 2);
        --flattening_iter;
        assert(*flattening_iter == 1);

        const std::chrono::duration<double> elapsed_time = std::chrono::steady_clock::now() - start_ts;
        assert(elapsed_time.count() < 0.5);
    }
}

int main() {
    TestProperties();
    TestSimple();
    TestEmpty();
    TestModify();
    TestStress();
    return 0;
}
а вот ошибки которые мне выводит при запуске проверки:
main.cpp: In function 'void TestModify()':
main.cpp:203:13: error: assignment of read-only location 'it.FlattenedVector<char>::Iterator::operator*()'
  203 |         *it = new_value;
      |         ~~~~^~~~~~~~~~~
main.cpp:207:15: error: assignment of read-only location 'it.FlattenedVector<char>::Iterator::operator[](1)'
  207 |         it[1] = value;
In file included from main.cpp:1:
flatten.h: In instantiation of 'T& FlattenedVector<T>::at(size_t) [with T = long int; size_t = long unsigned int]':
flatten.h:28:72:   required from 'T& FlattenedVector<T>::Iterator::operator*() [with T = long int]'
main.cpp:79:54:   required from here
flatten.h:178:48: error: binding reference of type 'long int&' to 'const __gnu_cxx::__alloc_traits<std::allocator<long int>, long int>::value_type' {aka 'const long int'} discards qualifiers
  178 |             return (*data_)[temp_idx][local_idx];
      |                                                ^
flatten.h: In instantiation of 'T& FlattenedVector<T>::at(size_t) [with T = int; size_t = long unsigned int]':
flatten.h:28:72:   required from 'T& FlattenedVector<T>::Iterator::operator*() [with T = int]'
main.cpp:93:9:   required from here
flatten.h:178:48: error: binding reference of type 'int&' to 'const __gnu_cxx::__alloc_traits<std::allocator<int>, int>::value_type' {aka 'const int'} discards qualifiers
flatten.h: In instantiation of 'T& FlattenedVector<T>::at(size_t) [with T = {anonymous}::TestData; size_t = long unsigned int]':
flatten.h:28:72:   required from 'T& FlattenedVector<T>::Iterator::operator*() [with T = {anonymous}::TestData]'
main.cpp:189:23:   required from here
flatten.h:178:48: error: binding reference of type '{anonymous}::TestData&' to 'const __gnu_cxx::__alloc_traits<std::allocator<{anonymous}::TestData>, {anonymous}::TestData>::value_type' {aka 'const {anonymous}::TestData'} discards qualifiers
flatten.h: In instantiation of 'T& FlattenedVector<T>::at(size_t) [with T = char; size_t = long unsigned int]':
flatten.h:28:72:   required from 'T& FlattenedVector<T>::Iterator::operator*() [with T = char]'
main.cpp:208:9:   required from here
flatten.h:178:48: error: binding reference of type 'char&' to 'const __gnu_cxx::__alloc_traits<std::allocator<char>, char>::value_type' {aka 'const char'} discards qualifiers
flatten.h: In instantiation of 'T& FlattenedVector<T>::at(size_t) [with T = long unsigned int; size_t = long unsigned int]':
flatten.h:28:72:   required from 'T& FlattenedVector<T>::Iterator::operator*() [with T = long unsigned int]'
main.cpp:244:13:   required from here
flatten.h:178:48: error: binding reference of type 'long unsigned int&' to 'const __gnu_cxx::__alloc_traits<std::allocator<long unsigned int>, long unsigned int>::value_type' {aka 'const long unsigned int'} discards qualifiers
make: *** [Makefile:35: main.o] Error 1