C++ C++;避免在钻头操作中完全移位 模板 类从 {//将骨灰盒包装为RNG 公众: 显式_Rng_from_urng(_urng&_Func) :_Ref(_Func),_Bits(CHAR_BIT*sizeof(_Udiff)),_Bmask(_Udiff(-1)) {//从URNG构造 对于(;(\u Urng::max)(-(\u Urng::min)(>=1) --_比特; } _Diff运算符()(_Diff_索引) {//adapt{u将闭合范围调整为[0,\u索引) 对于(;;) {//尝试一个随机值样本 _Udiff_Ret=0;//随机位 _Udiff _Mask=0;//2^N-1,_Ret在[0,_Mask]之内 而(_掩码从左向右分组

C++ C++;避免在钻头操作中完全移位 模板 类从 {//将骨灰盒包装为RNG 公众: 显式_Rng_from_urng(_urng&_Func) :_Ref(_Func),_Bits(CHAR_BIT*sizeof(_Udiff)),_Bmask(_Udiff(-1)) {//从URNG构造 对于(;(\u Urng::max)(-(\u Urng::min)(>=1) --_比特; } _Diff运算符()(_Diff_索引) {//adapt{u将闭合范围调整为[0,\u索引) 对于(;;) {//尝试一个随机值样本 _Udiff_Ret=0;//随机位 _Udiff _Mask=0;//2^N-1,_Ret在[0,_Mask]之内 而(_掩码从左向右分组,c++,bit,C++,Bit,shift operators>从左向右分组 移位表达式: 加法表达式 移位表达式>加法表达式 操作数应为整数或无范围枚举类型,并执行整数提升。结果类型为提升后的左操作数。如果右操作数为负,或大于或等于提升后的左操作数的位长度,则行为未定义。 7.6.7轮班操作员 shift operators>从左向右分组 移位表达式: 加法表达式 移位表达式>加法表达式 操作数应为整数或无范围枚举类型,并执行整数提升。结果类型为提升后的左操作数。如果右操作数为负,或大于或等于提升后的左操作数的位长度,则行为

shift operators>从左向右分组

移位表达式:

加法表达式

移位表达式>加法表达式

操作数应为整数或无范围枚举类型,并执行整数提升。结果类型为提升后的左操作数。如果右操作数为负,或大于或等于提升后的左操作数的位长度,则行为未定义。

7.6.7轮班操作员
  • shift operators>从左向右分组

    移位表达式:

    加法表达式

    移位表达式>加法表达式

    操作数应为整数或无范围枚举类型,并执行整数提升。结果类型为提升后的左操作数。如果右操作数为负,或大于或等于提升后的左操作数的位长度,则行为未定义。


  • 也就是说,如果
    \u位
    等于
    sizeof(\u Udiff)*CHAR\u位
    ,如果构造函数中没有输入for循环,可能会发生这种情况,那么移位被分为两个移位,以避免
    \u位
    等于
    sizeof(\u Udiff)时出现未定义的行为*字符位
    ,如果未输入构造函数中的for循环,则可能发生这种情况。
    template<class _Diff,
            class _Urng>
            class _Rng_from_urng
        {   // wrap a URNG as an RNG
        public:
            explicit _Rng_from_urng(_Urng& _Func)
                : _Ref(_Func), _Bits(CHAR_BIT * sizeof(_Udiff)), _Bmask(_Udiff(-1))
            {   // construct from URNG
                for (; (_Urng::max)() - (_Urng::min)() < _Bmask; _Bmask >>= 1)
                    --_Bits;
            }
    
            _Diff operator()(_Diff _Index)
            {   // adapt _Urng closed range to [0, _Index)
                for (;;)
                {   // try a sample random value
                    _Udiff _Ret = 0;    // random bits
                    _Udiff _Mask = 0;   // 2^N - 1, _Ret is within [0, _Mask]
    
                    while (_Mask < _Udiff(_Index - 1))
                    {   // need more random bits
                        _Ret <<= _Bits - 1; // avoid full shift
                        _Ret <<= 1;
                        _Ret |= _Get_bits();
                        _Mask <<= _Bits - 1;    // avoid full shift
                        _Mask <<= 1;
                        _Mask |= _Bmask;
                    }
    
                    // _Ret is [0, _Mask], _Index - 1 <= _Mask, return if unbiased
                    if (_Ret / _Index < _Mask / _Index
                        || _Mask % _Index == _Udiff(_Index - 1))
                        return (_Ret % _Index);
                }
            }
        };
    }
    
    _Ret <<= _Bits - 1; // avoid full shift 
    _Ret <<= 1;
    
    _Ret<<=_Bits;