我目前在使用位移运算符时遇到了问题。我对它不熟悉,所以请原谅我这个愚蠢的问题。
我有以下代码:
INT iBitShift = 82;
INT iMaxColumn = 82;
for ( iCol = 0; iCol < iMaxColumn; iCol++ ) {
dwColumnBit = (dwNewBitmap >> iBitShift) & 0x01;
if ( dwColumnBit ) {
// do something..
}
iBitShift--;
}当iMaxColumn小于30时,它工作得很好,但当它变成82时,问题已经开始出现了。发生的情况是,当iCol达到32和64时,dwColumnBit不再获得正确的值。我的代码中有什么错误吗?我读过关于循环移位的文章,但我不知道如何实现它。
提前感谢!
发布于 2011-03-09 17:21:38
从您的命名约定来看,我猜您正在尝试对DWORD执行位移位。DWORD是4字节,这意味着32位(在32位机器中)。因此,当你将一个DWORD移位32次后,你将在DWORD中得到所有的零。
此外,您的声明:
(dwNewBitmap >> iBitShift) & 0x01尝试移位超过32位,因为iBitShift是用82初始化的,这意味着考虑到只有32位可以移位,它将无法移位82位。
我希望这能澄清你觉得“奇怪”的行为。
编辑:基于评论中来自OP的一些信息:
看起来位图是以二进制数据的形式存储在注册表中的。您需要将该二进制数据读取到一个字节数组中,然后您可以分解您的逻辑,以便一次只从该数据中选取一个DWORD (在循环中执行此操作),然后在从1到32的循环中检查该DWORD的位。这样你就可以知道哪些位被置位了,哪些位没有置位。
发布于 2011-03-09 17:28:22
当你在单词边界上移动时,你会丢失一些比特。
您似乎想知道位iBitShift的值。您可能需要首先找到适当的字(使用iBitShift/wordsize),然后移位其余的位(使用iBitShift%wordsize):
template< typename T, int N >
bool bit( T (&words)[N], int iIndex ) {
static const size_t bitsperword =
sizeof(T)*numeric_limits<unsigned char>::digits;
// find proper word (assuming words[0] contains the first word)
T word = words[ iIndex/bitsperword ];
// shift the residue
word >>= iIndex%bitsperword;
return word & 0x1;
}
int main(){
int ints [] = {1,~0x0};
for( int i = 0; i != sizeof(int)*sizeof(ints); ++i ) {
printf("%d", bit(ints,i) ? 1:0);
}
return 0;
}发布于 2011-03-10 22:03:09
既然你最终承认你真的在这里做位图处理,你也可以考虑使用std::bitset<82>来完成这项任务。bitset也能够与string相互转换。最重要的是,它可以与枚举一起工作!
enum column {
colA, colB, ....
, colMAX // keep this one last
};
bitset<colMAX> columnvisible;
columnvisible.set(colB);
columnvisible.reset(colA);
...
storeStringInRegistry( columnvisible.tostring() );
...
columnvisible = bitset<colMAX>( readStringFromRegistry() );
for( column c = colA; c != colMAX; ++c ) {
if( columnvisible[c] ) displayColumn( c );
}很好,不是吗?
https://stackoverflow.com/questions/5243561
复制相似问题