Annotation of nono/lib/vectorbool64.h, revision 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.