位操作技巧

2021-08-29 09:08:52 字數 2700 閱讀 6982

檢測乙個無符號數是不為2^n-1(^為冪):x&(x+1)

將最右側0位改為1位:x | (x+1)

二進位制補碼運算公式:

-x = ~x + 1 = ~(x-1)

~x = -x-1

-(~x) = x+1

~(-x) = x-1

x+y = x - ~y - 1 = (x|y)+(x&y)

x-y = x + ~y + 1 = (x|~y)-(~x&y)

x^y = (x|y)-(x&y)

x|y = (x&~y)+y

x&y = (~x|y)-~x

x==y:    ~(x-y|y-x)

x!=y:    x-y|y-x

x< y:    (x-y)^((x^y)&((x-y)^x))

x<=y:    (x|~y)&((x^y)|~(y-x))

x< y:    (~x&y)|((~x|y)&(x-y))//

無符號x,y比較

x<=y:    (~x|y)&((x^y)|~(y-x))//無符號x,y比較

使用位運算的無分支**:

計算絕對值

int abs( int x )

符號函式:

sign(x) = -1, x<0; 0, x == 0 ; 1, x > 0

int sign(int x)

三值比較:

cmp(x,y) = -1, x y

int cmp( int x, int y )

doz=x-y, x>=y; 0, x int doz(int x, int y )

int max(int x, int y )

不使用第三方交換

x,y:

1.x ^= y ; y ^= x ; x ^= y ;

2.x = x+y ; y = x-y ; x = x-y ;

3.x = x-y ; y = y+x ; x = y-x ;

4.x = y-x ; x = y-x ; x = x+y ;

雙值交換:x = a, x==b; b, x==a//常規編碼為

x = x==a ? b :a ;

1.x = a+b-x ;

2.x = a^b^x ;

下捨入到2的k次方的倍數

: 1.x & ((-1)< 2.(((unsigned)x)>>k)<

上捨入:

1. t = (1< 2.t = (-1)<

位計數,統計1位的數量:

1. int pop(unsigned x)

2. int pop(unsigned x) ;

return table[x&0xff]+table[(x>>8)&0xff]+table[(x>>16)&0xff]+table[(x>>24)] ;

} 奇偶性計算

: x = x ^ ( x>>1 ) ;

x = x ^ ( x>>2 ) ;

x = x ^ ( x>>4 ) ;

x = x ^ ( x>>8 ) ;

x = x ^ ( x>>16 ) ;

結果中位於x最低位,對無符號x,結果的第i位是原數第i位到最左側位的奇偶性

位反**

unsigned rev(unsigned x)

遞增位反轉後的數:

unsigned inc_r(unsigned x)

while( x < m ) ;

return x ;

} 混選位:

abcd efgh ijkl mnop abcd efgh ijkl mnop->aabb ccdd eeff gghh iijj kkll mmnn oopp

unsigned ps(unsigned x)

位壓縮:

選擇並右移字x中對應於掩碼m的1位的位,如:

compress(abcdefgh,01010101)=0000bdfh

compress_left(x,m)操作與此類似,但結果位在左邊

: bdfh0000.

unsigned compress(unsigned x, unsigned m)

return x ;

} 位置換:

用32個5位數表示從最低位開始的位的目標位置,結果是乙個32*5的位矩陣,

將該矩陣沿次對角線轉置後用5個32位字p[5]存放。

sag(x,m) = compress_left(x,m) | compress(x,~m) ;

準備工作:

void init( unsigned *p )

實際置換:

int rep( unsigned x )

二進位製碼到gray碼的轉換

: unsigned b2g(unsigned b )

gray碼到二進位製碼

: unsigned g2b(unsigned g)

找出最左0位元組的位置

: int zbytel( unsigned x )

; unsigned y ;

y = (x&0x7f7f7f7f) + 0x7f7f7f7f ;

y = ~(y|x|0x7f7f7f7f) ;

return table[y*0x00204081 >> 28] ;//乘法可用移位和加完成

}

位操作技巧

檢測乙個無符號數是不為2 n 1 為冪 x x 1 將最右側0位改為1位 x x 1 二進位制補碼運算公式 x x 1 x 1 x x 1 x x 1 x x 1 x y x y 1 x y x y x y x y 1 x y x y x y x y x y x y x y y x y x y x ...

高效位操作技巧

檢測乙個無符號數是不為2 n 1 為冪 x x 1 將最右側0位改為1位 x x 1 二進位制補碼運算公式 x x 1 x 1 x x 1 x x 1 x x 1 x y x y 1 x y x y x y x y 1 x y x y x y x y x y x y x y y x y x y x ...

C C 位操作技巧

檢測乙個無符號數是不為2 n 1 為冪 x x 1 將最右側0位改為1位 x x 1 二進位制補碼運算公式 x x 1 x 1 x x 1 x x 1 x x 1 x y x y 1 x y x y x y x y 1 x y x y x y x y x y x y x y y x y x y x ...