Cod sursa(job #3251019)

Utilizator redstonegamer22Andrei Ion redstonegamer22 Data 24 octombrie 2024 16:40:56
Problema Secv8 Scor 5
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.94 kb
#pragma GCC optimize("Ofast")
#define LIBCXX_ENABLE_THREADS OFF
#include <bits/stdc++.h>
#include <ext/rope>

using namespace std;
using namespace __gnu_cxx;

#ifndef LOCAL
ifstream in("secv8.in");
ofstream out("secv8.out");
#define cin in
#define cout out
#endif // LOCAL

#include <iostream>
#include <memory>
#include <cassert>

#include <memory>  // For std::allocator_traits

#include <memory>  // For placement new and std::destroy_at

template <typename T>
class bump_allocator {
public:
    using value_type = T;

    // Static buffer for all instances of the allocator
    static constexpr std::size_t buffer_size = 1024 * 1024 * sizeof(T);  // Adjust buffer size to accommodate T
    static char buffer[buffer_size];  // Pre-allocated buffer as a char array (byte-addressable)
    static std::size_t offset;        // Current offset for bump allocation

    // Default constructor
    bump_allocator() = default;

    // Copy constructor (needed for rebind mechanism)
    template <typename U>
    bump_allocator(const bump_allocator<U>&) noexcept {
        // No state to copy, this is stateless
    }

    // Allocate memory for n objects of type T
    T* allocate(std::size_t n) {
        size_t space_required = n * sizeof(T);
        if (offset + space_required > buffer_size) {
            throw std::bad_alloc();  // Not enough space in the buffer
        }
        T* result = reinterpret_cast<T*>(buffer + offset);
        offset += space_required;
        return result;
    }

    // Deallocate is a no-op for a bump allocator
    void deallocate(T*, std::size_t) {
        // Bump allocators don't deallocate individual allocations
    }

    // Resets the allocator (only way to free all memory)
    static void reset() {
        offset = 0;
    }

    // Construct an object of type T in allocated memory
    template <typename U, typename... Args>
    void construct(U* p, Args&&... args) {
        ::new ((void*)p) U(std::forward<Args>(args)...);  // Placement new
    }

    // Destroy an object of type T
    template <typename U>
    void destroy(U* p) {
        p->~U();  // Explicitly call the destructor
    }

    // Comparison operators (necessary for allocator compatibility)
    bool operator==(const bump_allocator&) const noexcept {
        return true; // All instances are considered equal (stateless)
    }

    bool operator!=(const bump_allocator& other) const noexcept {
        return !(*this == other);
    }

    // Rebind allocator to a different value type (required for allocator compatibility)
    template <typename U>
    struct rebind {
        using other = bump_allocator<U>;  // Bump allocator can be used for any type U
    };
};

// Initialize static buffer and offset
template <typename T>
char bump_allocator<T>::buffer[bump_allocator<T>::buffer_size];

template <typename T>
std::size_t bump_allocator<T>::offset = 0;


int main()
{
    #ifndef LOCAL
        ios_base::sync_with_stdio(false);
        cin.tie(0); cout.tie(0);
    #endif // LOCAL

    rope<int, bump_allocator<int>> s; // Use the bump allocator here
    int k, c; cin >> k >> c;

    while(k--) {
        char t; cin >> t;
        if(t == 'I') {
            int p, x; cin >> p >> x; p--;
            s.insert(p, x);
            s.insert(s.size() - p, x);
        }
        if(t == 'A') {
            int p; cin >> p;
            cout << s[p - 1] << '\n';
        }
        if(t == 'R') {
            int l, r; cin >> l >> r; l--; r--;
            s = s.substr(0, l) + s.substr(s.size() - r - 1, r - l + 1) + s.substr(r + 1, s.size() - 2 * r - 2) + s.substr(l, r - l + 1) + s.substr(s.size() - l, l);
        }
        if(t == 'D') {
            int l, r; cin >> l >> r; l--; r--;
            s.erase(s.size() - r - 1, r - l + 1);
            s.erase(l, r - l + 1);
        }

        #ifdef LOCAL
            cerr << "\t\tS: "; for(auto e : s) cerr << e << " "; cerr << endl;
        #endif // LOCAL
    }

    s = s.substr(0, s.size() / 2);
    for(auto e : s) cout << e << " "; cout << '\n';

    return 0;
}