位運(yùn)算符在js中的使用

計(jì)算機(jī)中的數(shù)在內(nèi)存中都是以二進(jìn)制形式進(jìn)行存儲的蟹漓,用位運(yùn)算就是直接對整數(shù)在內(nèi)存中的二進(jìn)制位進(jìn)行操作棉圈,因此其執(zhí)行效率非常高实苞,在程序中盡量使用位運(yùn)算進(jìn)行操作剪廉,這會大大提高程序的性能烈涮。

位操作符

& 與運(yùn)算 兩個(gè)位都是 1 時(shí)朴肺,結(jié)果才為 1,否則為 0坚洽,如

1 0 0 1 1

&? 1 1 0 0 1

------------------------------

1 0 0 0 1

| 或運(yùn)算 兩個(gè)位都是 0 時(shí)戈稿,結(jié)果才為 0,否則為 1讶舰,如

1 0 0 1 1

|? 1 1 0 0 1

------------------------------

1 1 0 1 1

^ 異或運(yùn)算鞍盗,兩個(gè)位相同則為 0,不同則為 1跳昼,如

1 0 0 1 1

^? 1 1 0 0 1

-----------------------------

0 1 0 1 0

~ 取反運(yùn)算般甲,0 則變?yōu)?1,1 則變?yōu)?0鹅颊,如

~? 1 0 0 1 1

-----------------------------

0 1 1 0 0

?

<< 左移運(yùn)算敷存,向左進(jìn)行移位操作,高位丟棄堪伍,低位補(bǔ) 0历帚,如

int a = 8;

a << 3;

移位前:0000 0000 0000 0000 0000 0000 0000 1000

移位后:0000 0000 0000 0000 0000 0000 0100 0000

>> 右移運(yùn)算,向右進(jìn)行移位操作杠娱,對無符號數(shù)挽牢,高位補(bǔ) 0,對于有符號數(shù)摊求,高位補(bǔ)符號位禽拔,如

unsigned int a = 8;

a >> 3;

移位前:0000 0000 0000 0000 0000 0000 0000 1000

移位后:0000 0000 0000 0000 0000 0000 0000 0001

?

int a = -8;

a >> 3;

移位前:1111 1111 1111 1111 1111 1111 1111 1000

移位前:1111 1111 1111 1111 1111 1111 1111 1111


我們可能很少在編程中用位運(yùn)算,如果沒深入學(xué)習(xí),可能也很難理解睹栖。平時(shí)的數(shù)值運(yùn)算硫惕,其實(shí)是要先轉(zhuǎn)換成二進(jìn)制再進(jìn)行運(yùn)算的,而位運(yùn)算就是直接進(jìn)行二進(jìn)制運(yùn)算野来,所以位運(yùn)算的執(zhí)行效率肯定是更高的恼除。下面通過一些實(shí)例來加深對位運(yùn)算的理解。

按位與(&)

&&運(yùn)算符我們都知道曼氛,只有兩個(gè)都為真豁辉,結(jié)果才為真。&道理是一樣的舀患,只有兩個(gè)數(shù)的值為1時(shí)徽级,才返回1。例如1和3的按位與操作:

0001&0011---------0001

只有對應(yīng)的數(shù)為1時(shí)聊浅,結(jié)果才為1餐抢,其他都為0。

判斷一個(gè)數(shù)是奇數(shù)還是偶數(shù)低匙,我們會用求余數(shù)來判斷:

functionassert(n){if(n %2===1) {? ? console.log("n是奇數(shù)");? ? }else{? ? console.log("n是偶數(shù)");? }}assert(3); //"n是奇數(shù)"

我們也可以用一個(gè)數(shù)和1進(jìn)行按位&操作來判斷旷痕,而且速度更快:

functionassert(n){if(n &1) {? ? console.log("n是奇數(shù)");}else{? ? console.log("n是偶數(shù)");}}assert(3); //"n是奇數(shù)"

下面是位運(yùn)算過程:

1=00013=0011--------& =0001

奇數(shù)的二進(jìn)制碼的最后一位數(shù)肯定是1,而1只有最后一位為1顽冶,按位&操作之后欺抗,結(jié)果肯定只有最后一位數(shù)為1。而偶數(shù)的二進(jìn)制表示的最后一位數(shù)是0渗稍,和1進(jìn)行按位&操作佩迟,結(jié)果所有位數(shù)都為0团滥。

按位或(|)

|與||操作符的道理也是一樣的竿屹,只要兩個(gè)數(shù)中有一個(gè)數(shù)為1,結(jié)果就為1灸姊,其他則為0拱燃。

0001|0011---------0011

對浮點(diǎn)數(shù)向下求整,我們會用下面的方法:

varnum =Math.floor(1.1);// 1

我們也可以用位運(yùn)算來求整:

varnum=1.1|0;// 1

其實(shí)浮點(diǎn)數(shù)是不支持位運(yùn)算的力惯,所以會先把1.1轉(zhuǎn)成整數(shù)1再進(jìn)行位運(yùn)算碗誉,就好像是對浮點(diǎn)數(shù)向下求整。所以1|0的結(jié)果就是1父晶。

按位非(~)

按位非就是求二進(jìn)制的反碼:

varnum=1;// 二進(jìn)制 00000000000000000000000000000001varnum1 = ~num;// 二進(jìn)制 11111111111111111111111111111110

我們知道哮缺,js中的數(shù)字默認(rèn)是有符號的。有符號的32位二進(jìn)制的最高位也就是第一位數(shù)字代表著正負(fù)甲喝,1代表負(fù)數(shù)尝苇,0代表整數(shù)。那到底11111111111111111111111111111110等于多少呢?最高位為1代表負(fù)數(shù)糠溜,負(fù)數(shù)的二進(jìn)制轉(zhuǎn)化為十進(jìn)制:符號位不變淳玩,其他位取反加1。取反之后為10000000000000000000000000000001非竿,加1之后為10000000000000000000000000000010蜕着,十進(jìn)制為-2。

按位異或(^)

按位異或是兩個(gè)數(shù)中只有一個(gè)1時(shí)返回1红柱,其他情況返回0承匣。

0001^0011---------0010

數(shù)字與數(shù)字本身按位異或操作得到的是0,因?yàn)槊績蓚€(gè)對應(yīng)的數(shù)字都相同豹芯,所以最后返回的都是0悄雅。

我們經(jīng)常會需要調(diào)換兩個(gè)數(shù)字的值:

var num1 = 1, num2 = 2, temp;

temp = num1;

num1 = num2; // 2

num2 = temp; // 1

如果裝逼一點(diǎn)的話,可以這樣:

var num1 = 1, num2 = 2;num1 = [num2, num2 = num1][0];console.log(num1); // 2console.log(num2); // 1

如果想再裝的穩(wěn)一點(diǎn)的話铁蹈,可以這樣:

varnum1 =1, num2 =2;num1 ^= num2;// num1 = num1 ^ num2 = 1 ^ 2 = 3num2 ^= num1;// num2 = num2 ^ (num1 ^ num2) = 2 ^ (1 ^ 2) = 1num1 ^= num2;// num1 = num1 ^ num2 = 3 ^ 1 = 2console.log(num1);// 2console.log(num2);// 1

有符號左移(<<)

有符號左移會將32位二進(jìn)制數(shù)的所有位向左移動(dòng)指定位數(shù)宽闲。如:

varnum=2;// 二進(jìn)制10num=num<<5;// 二進(jìn)制1000000,十進(jìn)制64

如果要求2的n次方握牧,可以這樣:

functionpower(n){return1<< n;}power(5);// 32

1的二進(jìn)制是01容诬,左移5位就是0100000,十進(jìn)制就是2的5次方32沿腰。

有符號右移(>>)

有符號右移會將32位二進(jìn)制數(shù)的所有位向右移動(dòng)指定位數(shù)览徒。如:

varnum=64;// 二進(jìn)制1000000num=num>>5;// 二進(jìn)制10,十進(jìn)制2

求一個(gè)數(shù)的二分之一:

var num =64>> 1;//32

有符號左移與右移不會影響符號位颂龙。

無符號右移(>>>)

正數(shù)的無符號右移與有符號右移結(jié)果是一樣的习蓬。負(fù)數(shù)的無符號右移會把符號位也一起移動(dòng),而且無符號右移會把負(fù)數(shù)的二進(jìn)制碼當(dāng)成正數(shù)的二進(jìn)制碼:

varnum=-64;// 11111111111111111111111111000000num=num>>>5;// 134217726

所以措嵌,我們可以利用無符號右移來判斷一個(gè)數(shù)的正負(fù):

functionisPos(n){return(n === (n >>>0)) ?true:false;? ? }isPos(-1);// falseisPos(1);// true

-1>>>0雖然沒有向右移動(dòng)位數(shù)躲叼,但-1的二進(jìn)制碼已經(jīng)變成了正數(shù)的二進(jìn)制碼:

11111111111111111111111111111111

所以-1>>>0的值為4294967295。

~~用來取整

~~3.5? ? 3

~~-2.6? ?-2

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末企巢,一起剝皮案震驚了整個(gè)濱河市枫慷,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌浪规,老刑警劉巖或听,帶你破解...
    沈念sama閱讀 217,509評論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異笋婿,居然都是意外死亡誉裆,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,806評論 3 394
  • 文/潘曉璐 我一進(jìn)店門缸濒,熙熙樓的掌柜王于貴愁眉苦臉地迎上來足丢,“玉大人元镀,你說我怎么就攤上這事■Γ” “怎么了栖疑?”我有些...
    開封第一講書人閱讀 163,875評論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長滔驶。 經(jīng)常有香客問我遇革,道長,這世上最難降的妖魔是什么揭糕? 我笑而不...
    開封第一講書人閱讀 58,441評論 1 293
  • 正文 為了忘掉前任萝快,我火速辦了婚禮,結(jié)果婚禮上著角,老公的妹妹穿的比我還像新娘揪漩。我一直安慰自己,他們只是感情好吏口,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,488評論 6 392
  • 文/花漫 我一把揭開白布奄容。 她就那樣靜靜地躺著,像睡著了一般产徊。 火紅的嫁衣襯著肌膚如雪昂勒。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,365評論 1 302
  • 那天舟铜,我揣著相機(jī)與錄音戈盈,去河邊找鬼。 笑死谆刨,一個(gè)胖子當(dāng)著我的面吹牛塘娶,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播痊夭,決...
    沈念sama閱讀 40,190評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼刁岸,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了生兆?” 一聲冷哼從身側(cè)響起难捌,我...
    開封第一講書人閱讀 39,062評論 0 276
  • 序言:老撾萬榮一對情侶失蹤膝宁,失蹤者是張志新(化名)和其女友劉穎鸦难,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體员淫,經(jīng)...
    沈念sama閱讀 45,500評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡合蔽,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,706評論 3 335
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了介返。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片拴事。...
    茶點(diǎn)故事閱讀 39,834評論 1 347
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡沃斤,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出刃宵,到底是詐尸還是另有隱情衡瓶,我是刑警寧澤,帶...
    沈念sama閱讀 35,559評論 5 345
  • 正文 年R本政府宣布牲证,位于F島的核電站哮针,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏坦袍。R本人自食惡果不足惜十厢,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,167評論 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望捂齐。 院中可真熱鬧蛮放,春花似錦、人聲如沸奠宜。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,779評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽压真。三九已至徘六,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間榴都,已是汗流浹背待锈。 一陣腳步聲響...
    開封第一講書人閱讀 32,912評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留嘴高,地道東北人竿音。 一個(gè)月前我還...
    沈念sama閱讀 47,958評論 2 370
  • 正文 我出身青樓,卻偏偏與公主長得像拴驮,于是被迫代替她去往敵國和親春瞬。 傳聞我的和親對象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,779評論 2 354

推薦閱讀更多精彩內(nèi)容