|
|
1.1 root 1: //
2: // nono
1.1.1.4 root 3: // Copyright (C) 2020 nono project
4: // Licensed under nono-license.txt
1.1 root 5: //
6:
1.1.1.3 root 7: #pragma once
8:
1.1 root 9: #include "header.h"
10: #include <vector>
11:
12: // 固定長キュー
13: // std::queue では出来ないことがいくつかあるので仕方なく車輪の再開発。
1.1.1.6 ! root 14: // std::vector を親に使っているが empty() と Empty() の動作が異なるなど
! 15: // しているため public にせず private 継承している。
1.1 root 16: //
17: // T 型で上限 capacity 個のキュー。
18: // スレッドセーフではない。
19: template <typename T, int capacity>
20: class FixedQueue
1.1.1.6 ! root 21: : private std::vector<T>
1.1 root 22: {
1.1.1.6 ! root 23: using inherited = std::vector<T>;
1.1 root 24: public:
25: // コンストラクタ
26: FixedQueue()
1.1.1.6 ! root 27: : inherited(capacity)
1.1 root 28: {
29: }
30:
31: // デストラクタ
32: virtual ~FixedQueue() {
33: }
34:
35: // 空にする
36: void Clear() {
37: start = 0;
38: length = 0;
39: }
40:
1.1.1.6 ! root 41: // 空きがあれば追加して true を返す。
! 42: // 空きがなければ何もせず false を返す。
1.1 root 43: bool Enqueue(T val) {
1.1.1.6 ! root 44: if (IsFull()) {
! 45: return false;
! 46: } else {
! 47: (*this)[(start + length) % capacity] = val;
1.1 root 48: length++;
49: return true;
50: }
51: }
52:
1.1.1.6 ! root 53: // 空きがなければ古いのを捨てて追加する。
! 54: void EnqueueForce(T val) {
! 55: if (IsFull()) {
! 56: Dequeue();
! 57: }
! 58: Enqueue(val);
! 59: }
! 60:
1.1 root 61: // 取り出し
62: // 要素が1つ以上あれば *outp に取り出して true を返す。
63: // キューが空なら false を返す。
64: bool Dequeue(T *outp) {
65: if (length > 0) {
66: // 1つ以上あれば取り出し
1.1.1.6 ! root 67: *outp = (*this)[start];
1.1 root 68: start = (start + 1) % capacity;
69: length--;
70: return true;
71: } else {
72: return false;
73: }
74: }
75:
76: // 取り出し
77: // 先頭の要素を取り出して返す。
1.1.1.6 ! root 78: // キューが空の時に呼ぶと T() が返る。
1.1 root 79: T Dequeue() {
80: if (length > 0) {
1.1.1.6 ! root 81: T val = (*this)[start];
1.1 root 82: start = (start + 1) % capacity;
83: length--;
1.1.1.6 ! root 84: return val;
! 85: } else {
! 86: return T();
1.1 root 87: }
88: }
89:
90: // 現在の要素数を取得
91: uint Length() const {
92: return length;
93: }
94:
1.1.1.6 ! root 95: // 要素が空なら true を返す
! 96: bool Empty() const {
! 97: return (length == 0);
! 98: }
! 99:
1.1.1.2 root 100: // 要素が一杯なら true を返す
101: bool IsFull() const {
1.1.1.6 ! root 102: return (Length() >= capacity);
1.1.1.2 root 103: }
104:
1.1 root 105: // 要素を覗き見る。
106: // idx は 0 .. length-1 までで、0 がキューの先頭。
1.1.1.3 root 107: T Peek(int idx) const {
1.1 root 108: // XXX 範囲チェックすべきだがとりあえず
1.1.1.6 ! root 109: return (*this)[(start + idx) % capacity];
! 110: }
! 111:
! 112: // 要素数を返す
! 113: constexpr int Capacity() const {
! 114: return capacity;
1.1 root 115: }
116:
117: private:
1.1.1.5 root 118: uint start {}; // 開始位置
119: uint length {}; // 現在有効な長さ
1.1 root 120: };
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.