Annotation of nono/lib/vectorbool64.h, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (C) 2026 Tetsuya Isaki
                      3:  *
                      4:  * Permission to use, copy, modify, and/or distribute this software for any
                      5:  * purpose with or without fee is hereby granted.
                      6:  *
                      7:  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
                      8:  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
                      9:  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
                     10:  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
                     11:  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
                     12:  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
                     13:  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
                     14:  */
                     15: 
                     16: #pragma once
                     17: 
                     18: #include "header.h"
                     19: #include <vector>
                     20: 
                     21: // uint64 に 64 ビットを詰め込んだ std::vector<bool> っぽいクラス。
                     22: // std::vector<bool> 特殊化より制約と抽象度を少し下げたもので、
                     23: // 内部構造が uint64 であることを見せている。
                     24: // 現状 capacity の概念はなく、要素数は64個単位で増減する。
                     25: //
                     26: // std::vector 互換のメソッドは小文字(というか同名)にする。
                     27: class VectorBool64
                     28: {
                     29:        static constexpr std::size_t NBITS = 64;
                     30: 
                     31:  public:
                     32:        // 初期サイズ 0 で作成する。
                     33:        VectorBool64() { }
                     34:        // 初期サイズを指定して作成する。初期値は false。
                     35:        explicit VectorBool64(std::size_t bits) {
                     36:                Resize(bits);
                     37:        }
                     38:        // 初期サイズと初期値を指定して作成する。
                     39:        VectorBool64(std::size_t bits, const bool c) {
                     40:                Resize(bits, c);
                     41:        }
                     42: 
                     43:        // デストラクタ不要。
                     44: 
                     45:        // デフォルト値を設定する。
                     46:        void SetDefault(bool c) {
                     47:                defval = c;
                     48:        }
                     49: 
                     50:        // 要素数(ビット数) を返す。std::vector 互換のはず。
                     51:        std::size_t size() const noexcept { return capacity(); }
                     52: 
                     53:        // メモリを再確保せずに格納できる要素数を返す。std::vector 互換のはず。
                     54:        std::size_t capacity() const noexcept { return value.size() * NBITS; }
                     55: 
                     56:        // 64 ビットバケット数を返す。
                     57:        std::size_t DataSize() const noexcept { return value.size(); }
                     58: 
                     59:        // コンテナが空なら true を返す。std::vector 互換のはず。
                     60:        bool empty() const noexcept { return value.empty(); }
                     61: 
                     62:        // 初期値 b を指定して要素数(ビット数)を sz に変更する。
                     63:        // ただし bits が 64 で割り切れない場合は 64 単位に切り上げる。
                     64:        void Resize(std::size_t sz, const bool b) {
                     65:                auto n = howmany(sz, NBITS);
                     66:                if (n != value.size()) {
                     67:                        uint64 initval = b ? -1 : 0;
                     68:                        value.resize(n, initval);
                     69:                }
                     70:        }
                     71:        void Resize(std::size_t sz) { Resize(sz, defval); }
                     72: 
                     73:        // 要素数(ビット数)を sz まで増やす。
                     74:        // つまり増える方向だけの Resize(sz, c)。
                     75:        void Expand(std::size_t sz, const bool c) {
                     76:                auto n = howmany(sz, NBITS);
                     77:                if (n > size()) {
                     78:                        Resize(sz, c);
                     79:                }
                     80:        }
                     81:        void Expand(std::size_t sz) { Expand(sz, defval); }
                     82: 
                     83:        // n 番目のビットを返す。
                     84:        // n が範囲外なら defval を返す。
                     85:        bool GetBit(std::size_t n) const {
                     86:                if (__predict_false(n >= size())) {
                     87:                        return defval;
                     88:                }
                     89:                std::size_t idx = n / NBITS;
                     90:                std::size_t off = n % NBITS;
                     91:                return ((GetData(idx) >> off) & 1) ? true : false;
                     92:        }
                     93: 
                     94:        // n 番目にビットを b に更新する。
                     95:        // n が範囲外なら何もしない?
                     96:        void SetBit(std::size_t n, bool b) {
                     97:                if (__predict_false(n >= size())) {
                     98:                        return;
                     99:                }
                    100:                std::size_t idx = n / NBITS;
                    101:                std::size_t off = n % NBITS;
                    102:                uint64 val = GetData(idx);
                    103:                if (b) {
                    104:                        val |= 1ULL << off;
                    105:                } else {
                    106:                        val &= ~(1ULL << off);
                    107:                }
                    108:                SetData(idx, val);
                    109:        }
                    110:        // n 番目のビットを立てる。オーバーロード…。
                    111:        void SetBit(std::size_t n) { SetBit(n, true); }
                    112:        // n 番目のビットをクリアする。
                    113:        void ClearBit(std::size_t n) { SetBit(n, false); }
                    114: 
                    115:        // idx 番目の 64 ビットバケットを返す。
                    116:        // idx が範囲外なら defval で構成された 64 ビットを返す。
                    117:        uint64 GetData(std::size_t idx) const noexcept {
                    118:                if (idx < value.size()) {
                    119:                        return value[idx];
                    120:                } else {
                    121:                        return defval ? -1 : 0;
                    122:                }
                    123:        }
                    124: 
                    125:        // data を idx 番目の 64 ビットバケットを代入する。
                    126:        // idx が範囲外なら何もしない?
                    127:        void SetData(std::size_t idx, uint64 data) {
                    128:                if (idx < value.size()) {
                    129:                        value[idx] = data;
                    130:                } else {
                    131:                        // どうする?
                    132:                }
                    133:        }
                    134: 
                    135:  private:
                    136:        std::vector<uint64> value {};
                    137: 
                    138:        // デフォルト値。
                    139:        // 要素数を拡大した時の初期値と、範囲外を読んだ時の値に使われる。
                    140:        bool defval {};
                    141: };

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.