Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/130.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 不跨越字节的除法_C++_Math_Biginteger_Integer Division - Fatal编程技术网

C++ 不跨越字节的除法

C++ 不跨越字节的除法,c++,math,biginteger,integer-division,C++,Math,Biginteger,Integer Division,我试图在一个由2个uint64\u ts组成的uint128\u t上除法。奇怪的是,该函数只适用于设置了较低的值而上限值为0的uint64_ts。我不明白为什么 这是除法和位移位的代码 class uint128_t{ private: uint64_t UPPER, LOWER; public: // lots of stuff uint128_t operator<<(int shift){ uint128_t ou

我试图在一个由2个
uint64\u t
s组成的
uint128\u t
上除法。奇怪的是,该函数只适用于设置了较低的值而上限值为0的
uint64_t
s。我不明白为什么

这是除法和位移位的代码

class uint128_t{
   private:
      uint64_t UPPER, LOWER;
   public:
      // lots of stuff

    uint128_t operator<<(int shift){
        uint128_t out;
        if (shift >= 128)
            out = uint128_t(0, 0);
        else if ((128 > shift) && (shift >= 64))
            out = uint128_t(LOWER << (64 - shift), 0);
        else if (shift < 64)
            out = uint128_t((UPPER << shift) + (LOWER >> (64 - shift)), LOWER << shift);
        return out;
    }

    uint128_t operator<<=(int shift){
        *this = *this << shift;
        return *this;
    }

    uint128_t operator/(uint128_t rhs){
            // copy of numerator = copyn
            uint128_t copyn(*this), quotient = 0;// constructor: uint128_t(T), uint128_t(S, T), uint128_t(uint128_t), etc
            while (copyn >= rhs){
                // copy of denomiator = copyd
                // temp is the current quotient bit being worked with
                uint128_t copyd(rhs), temp(1);
                // shift the divosr to the highest bit
                while (copyn > (copyd << 1)){
                    copyd <<= 1;
                    temp <<= 1;
                }
                copyn -= copyd;
                quotient += temp;
            }
            return quotient;
        }
// more stuff
};
类uint128\u t{
私人:
uint64_t上部、下部;
公众:
//很多东西
uint128(操作员班次)和(班次>=64))
out=uint128\u t(低位(64-shift)),低位
out=uint128\u t(低位试试这个:

// some bit operations stuff
const unsigned char de_brujin_bit_map_64 [] = 
{
    0,1,2,7,3,13,8,19,4,25,14,28,9,34,20,40,5,17,26,38,15,46,29,48,10,31,35,54,21,50,41,57,
    63,6,12,18,24,27,33,39,16,37,45,47,30,53,49,56,62,11,23,32,36,44,52,55,61,22,43,51,60,42,59,58
};
inline uint8_t trailing_zero_count(uint64_t x) { return x?de_brujin_bit_map_64[(lower_bit(x)*0x0218A392CD3D5DBFL) >> 58]:64; }
inline uint8_t leading_zero_count(uint64_t x) { return x?(63-de_brujin_bit_map_64[(upper_bit(x)*0x0218A392CD3D5DBFL) >> 58]):64; }
inline uint64_t lower_bit(uint64_t x) { return x & -(int64_t&)x; }
inline uint64_t upper_bit(uint64_t x)
{
    if(!x) return 0;
    x |= x >> 1; x |= x >> 2; x |= x >> 4; x |= x >> 8; x |= x >> 16;  x |= x >> 32;
    return (x >> 1) + 1;
}
inline uint128_t upper_bit(const uint128_t x) 
{
    if(x.upper()) return uint128_t(upper_bit(x.upper()), 0); 
    else return uint128_t(0, upper_bit(x.lower())); 
}
inline uint128_t lower_bit(const uint128_t x) 
{
    if(x.lower()) return uint128_t(0, lower_bit(x.lower())); 
    else return uint128_t(lower_bit(x.upper()), 0); 
}
inline uint8_t trailing_zero_count(const uint128_t& x) { return x.lower()?trailing_zero_count(x.lower()):(64+trailing_zero_count(x.upper())); }
inline uint8_t leading_zero_count(const uint128_t& x) { return x.upper()?leading_zero_count(x.upper()):(64+leading_zero_count(x.lower())); }

// division operator
uint128_t uint128_t::operator/(const uint128_t& rhs) const
{
    if(rhs == 0) return uint128_t(0); // !!!! zero division
    if(rhs == rhs) return uint128_t(1);
    if(rhs > *this) return uint128_t(0);
    if(rhs == 1) return *this;
    if(!upper_ && !rhs.upper_) return uint128_t(0, lower_/rhs.lower_);
    if(lower_bit(rhs) == rhs) return *this >> trailing_zero_count(rhs);
    uint128_t result;
    uint128_t bit_mask = upper_bit();
    uint128_t denom = 1;
    do 
    {
        bit_mask >>= 1;
        denom <<= 1;
        if(*this & bit_mask) denom |= 1;
        result <<= 1;
        if(denom >= rhs) { denom -= rhs; result |= 1; }
    } 
    while (bit_mask.lower_ != 1);
    return result;
}
//一些位操作的东西
const unsigned char de_brujin_bit_map_64[]=
{
0,1,2,7,3,13,8,19,4,25,14,28,9,34,20,40,5,17,26,38,15,46,29,48,10,31,35,54,21,50,41,57,
63,6,12,18,24,27,33,39,16,37,45,47,30,53,49,56,62,11,23,32,36,44,52,55,61,22,43,51,60,42,59,58
};
内联uint8_t training_zero_count(uint64_t x){return x?de_brujin_bit_map_64[(低位(x)*0x0218A392CD3D5DBFL)>>58]:64;}
内联uint8前导零计数(uint64\UTX){return x?(63位映射64[(高位(x)*0x0218A392CD3D5DBFL)>>58]):64;}
内联uint64\u t低位(uint64\u t x){return x&-(int64\u t&)x;}
内联uint64\u t高位(uint64\u t x)
{
如果(!x)返回0;
x |=x>>1;x |=x>>2;x |=x>>4;x |=x>>8;x |=x>>16;x |=x>>32;
返回(x>>1)+1;
}
内联uint128\u t高位(常数uint128\u t x)
{
如果(x.upper())返回uint128_t(高位(x.upper()),则为0;
否则返回uint128_t(0,高位(x.lower());
}
内联uint128\u t低位(常数uint128\u t x)
{
如果(x.lower())返回uint128_t(0,低位(x.lower()));
否则返回uint128(低位(x.upper()),0);
}
inline uint8_t training_zero_count(const uint128_t&x){返回x.lower()?training_zero_count(x.lower()):(64+training_zero_count(x.upper());}
内联uint8_t前导零计数(const uint128_t&x){返回x.upper()?前导零计数(x.upper()):(64+前导零计数(x.lower());}
//除法运算符
uint128_t uint128_t::运算符/(常数uint128_t&rhs)常数
{
如果(rhs==0)返回uint128_t(0);/!!零除法
如果(rhs==rhs)返回uint128_t(1);
如果(rhs>*此)返回uint128\u t(0);
如果(rhs==1)返回*this;
如果(!upper&&!rhs.upper&)返回uint128(0,lower&/rhs.lower&);
如果(低位(rhs)=rhs)返回*此>>尾随的零计数(rhs);
uint128_t结果;
uint128位掩码=高位();
uint128_t denom=1;
做
{
位掩码>>=1;

不管怎样,这个版本要快一点:)

确保针对127次迭代进行4000次迭代:

uint128_t divident = uint128_t(0xffffffffffffffffULL, 0xffffffffffffffffULL);
uint128_t divisor = 10;
{
    uint32_t iter_count = 0;
    uint128_t copyn(divident), quotient = 0;
    while (copyn >= divisor)
    {
        ++iter_count;
        uint128_t copyd(divisor), temp(1);
        while ((copyn >> 1) > copyd) { ++iter_count; copyd <<= 1; temp <<= 1; }
        copyn -= copyd;
        quotient += temp;
    }
    std::cout << "iterations: " << std::dec << iter_count << std::endl;
}
{
    uint32_t iter_count = 0;
    uint128_t bit_pos = dtl::bits::upper_bit(divident);
    uint128_t tmp = 1, quotient = 0;
    do 
    {
        ++iter_count;
        bit_pos >>= 1;
        tmp <<= 1;
        if(divident & bit_pos) tmp |= 1;
        quotient <<= 1;
        if(tmp >= divisor) { tmp -= divisor; quotient |= 1; }
    } 
    while (bit_pos != 1);
    std::cout << "iterations: " << std::dec << iter_count << std::endl;
}
uint128\u t divident=uint128\u t(0xfffffffffffffull,0xfffffffffffffffull);
uint128_t除数=10;
{
uint32的iter计数=0;
uint128_t copyn(divident),商=0;
while(copyn>=除数)
{
++iter_计数;
uint128_t copyd(除数),temp(1);

虽然((copyn>>1)>copyd){++iter\u count;copyd实际上,所有的caps通常都是为预处理器标识符保留的。有些预处理器标识符实际上是常量,所以他仍然是对的,但从更广泛的意义上说,所有宏都是用衣壳编写的,没有任何改变(除法运算符有什么问题吗?它似乎卡在
中,而(copyn>(copyd