——————————————————————————————————————————
template<long N,template<long,typename>class __Alloc>
bool HugeNumberBase<N,__Alloc>::EqualValue(unsigned long value) const{
if(data_[N-1]==value){
for(long i=0;i<N-1;i++)
if(data_[i])
return false;
return true;
}
return false;
}
template<long N,template<long,typename>class __Alloc>
long HugeNumberBase<N,__Alloc>::HighestBit() const{
long at=0;
while(at<N&&!data_[at])
at++;
if(at>=N)
return 0;
long t(0);
while(!((data_[at]<<t)&SignBit))
t++;
return (N-at)*EachBits-t-1;
}
template<long N,template<long,typename>class __Alloc>
long HugeNumberBase<N,__Alloc>::LowestBit() const{
long at(N-1);
while(at>=0&&!data_[at])
at--;
if(at<0)
return 0;
long t(0);
while(!((data_[at]>>t)&1))
t++;
return (N-1-at)*EachBits+t;
}
template<long N,template<long,typename>class __Alloc>
HugeNumberBase<N,__Alloc> & HugeNumberBase<N,__Alloc>::ResetHigherBits(long Position){
long at(N-1-Position/EachBits);
for(long i=0;i<at;i++)
data_[i]=0;
data_[at]&=(1<<(Position%EachBits))-1;
return *this;
}
——————————————————————————————————————————
这段代码包括4个函数:
EqualValue
HighestBit
LowestBit
ResetHigherBits
函数EqualValue很简单,即判断当前大整数是否和参数value相等。首先它看大整数的最低32 bits(data_[N-1])是否和value相等,然后判断其他高位bits是否为0。
这个函数存在的原因是:如果用OperatorEqual来判断大整数与给定的unsigned long是否相等,是“杀鸡用牛刀”,会因为生成临时HugeNumberBase而降低效率。
函数HighestBit和的功能也很简单,得到大整数最高(最低)比特1的位置,比如一个64 bits的大整数是0x 30 00 00 00 50 00 00 08,它的最高比特1就是30里面最高位的那个比特1,位置是61(从0开始算);而它的最低比特1就是08里最低的比特1,位置是3(从0开始)。
它们的作用清楚了,代码也就很明朗了。
在HighestBit中:
long at=0;
while(at<N&&!data_[at])
at++;
if(at>=N)
return 0;
找到高位中第一个不是0的data_,如果大整数本来就是0,那么返回0;
接着在data_[at]找最高位的比特1,这通过把data_[at]向左移t位,再看第31比特位是否为1来实现:
long t(0);
while(!((data_[at]<<t)&SignBit))
t++;
最后在return里计算比特1的位置。
在LowestBit则正好相反:
long at(N-1);
while(at>=0&&!data_[at])
at--;
if(at<0)
return 0;
找到低位中第一个不是0的data_,如果大整数本来就是0,那么返回0;
接着在data_[at]找最低位的比特1,这通过把data_[at]向右移t位,再与1进行And操作来判断:
long t(0);
while(!((data_[at]>>t)&1))
t++;
最后同样在return中计算比特1的位置。
函数ResetHigherBits的作用是:把大整数里所有大于Position的比特位都置0,Position位置从0开始计算。比如0x1234,如果把Position=2以上的所有比特位置0,那么将变成0x4。
这个过程包含2步:
long at(N-1-Position/EachBits);
for(long i=0;i<at;i++)
data_[i]=0;
根据Position计算出分界点在data_[at]内,然后把data_[at]高位(0 <= i < at)全部置0;
data_[at]&=(1<<(Position%EachBits))-1;
由Position%EachBits计算出在data_[at]内比特0与1的分界位置,然后只保留需要的比特1。