93 lines
1.4 KiB
C++
93 lines
1.4 KiB
C++
#pragma once
|
|
|
|
#include <cstddef>
|
|
#include <utility>
|
|
|
|
#include <mtl/exception.hpp>
|
|
|
|
namespace mtl {
|
|
|
|
/**
|
|
* \brief Statically allocated queue
|
|
*/
|
|
template <typename T>
|
|
class iqueue {
|
|
private:
|
|
T* m_buf;
|
|
size_t m_size;
|
|
const size_t m_capacity;
|
|
|
|
size_t m_begin;
|
|
size_t m_end;
|
|
|
|
public:
|
|
using value_type = T;
|
|
using size_type = size_t;
|
|
using reference = T&;
|
|
using const_reference = const T&;
|
|
|
|
iqueue(T* buf, size_t capacity) noexcept : m_buf(buf), m_capacity(capacity), m_begin(0), m_end(0) {}
|
|
|
|
reference front() noexcept {
|
|
return m_buf[m_begin];
|
|
}
|
|
const_reference front() const noexcept {
|
|
return m_buf[m_begin];
|
|
}
|
|
const_reference cfront() const noexcept {
|
|
return m_buf[m_begin];
|
|
}
|
|
|
|
reference back() noexcept {
|
|
return m_buf[m_end];
|
|
}
|
|
const_reference back() const noexcept {
|
|
return m_buf[m_end];
|
|
}
|
|
const_reference cback() const noexcept {
|
|
return m_buf[m_end];
|
|
}
|
|
|
|
bool empty() const noexcept {
|
|
return m_size == 0;
|
|
}
|
|
size_t size() const noexcept {
|
|
return m_size;
|
|
}
|
|
|
|
void push(T value) {
|
|
if (m_size == m_capacity) {
|
|
throw mtl::length_error();
|
|
}
|
|
|
|
m_buf[m_end] = std::move(value);
|
|
|
|
++m_size;
|
|
|
|
++m_end;
|
|
m_end %= m_capacity;
|
|
}
|
|
void pop() noexcept {
|
|
if (m_size == 0) {
|
|
return;
|
|
}
|
|
|
|
--m_size;
|
|
|
|
++m_begin;
|
|
m_begin %= m_capacity;
|
|
}
|
|
};
|
|
|
|
template <typename T, size_t C>
|
|
class queue : public iqueue<T> {
|
|
private:
|
|
T m_buf[C];
|
|
|
|
public:
|
|
queue() noexcept : iqueue<T>(m_buf, C) {}
|
|
};
|
|
|
|
} // namespace mtl
|
|
|