Các toán tử Bitwise

1. Bitwise

Trong lập trình máy tính kỹ thuật số. Phép toán bitwise hoạt động trên một hoặc nhiều số nhị phân (binary numerals), hoặc các chuỗi giống số nhị phân. Đây là một phép toán đơn giản và nhanh, được hỗ trợ trực tiếp bởi bộ xử lý (processor). Thông thường các phép tính bitwise nhanh hơn rất nhiều so với phép nhân, phép chia, đôi khi nhanh hơn đáng kể so với phép cộng. Các phép tính bitwise sử dụng ít năng lượng hơn bởi nó ít sử dụng tài nguyên.Có 7 phép toán bitwise:

OperatorNameDescription
&ANDNếu cả 2 bit là 1, giá trị trả về là 1, ngược lại trả về 0.
|ORNếu một trong hai bit là 1, giá trị trả về là 1, ngược lại trả về 0.
^XORNếu hai bit khác nhau, giá trị trả về là 1, ngược lại trả về 0.
~NOTĐảo ngược tất cả các bit, 0 thành 1 và 1 thành 0.
<<Zero fill left shiftDịch chuyển tất cả các bit sang bên trái.
>>Signed right shiftDịch chuyển tất cả các bit sang bên phải ngoại trừ bit đầu tiên.
>>>Zero fill right shiftDịch chuyển tất cả các bit sang bên phải.
Bitwise AND

Khi một bitwise AND được thực hiện trên một cặp bit, nó trả về 1 nếu cả 2 bit là 1, ngược lại trả về 0.Ví dụ với 1 bit:

OperationResult
0 & 00
0 & 10
1 & 00
1 & 11

Ví dụ với 4 bit:

OperationResult
1111 & 00000000
1111 & 00010001
1111 & 00100010
1111 & 01000100
Bitwise OR:

Khi một bitwise OR được thực hiện trên một cặp bit, nó trả về 1 nếu một trong các bit là 1, ngược lại trả về 0.Ví dụ với 1 bit:

OperationResult
0 | 00
0 | 1
1 | 01
1 | 11

Ví dụ với 4 bit:

OperationResult
1111 | 00001111
1111 | 00011111
1111 | 00101111
1111 | 01001111
Bitwise XOR

Khi một bitwise XOR được thực hiện trên một cặp bit, nó trả về 1 nếu các bit khác nhau, ngược lại trả về 0.Ví dụ với 1 bit:

OperationResult
0 ^ 00
0 ^ 1
1 ^ 01
1 ^ 1

Ví dụ với 4 bit:

OperationResult
1111 ^ 00001111
1111 ^ 00011110
1111 ^ 00101101
1111 ^ 01001011
Bitwise NOT

Khi một Bitwise NOT được sử dụng nó sẽ đảo ngược tất cả các bit. 1 thành 0, và 0 thành 1.Ví dụ với 1 bit:

OperationResult
~ 01
~ 10

Ví dụ với 4 bit:

OperationResult
~ 00001111
~ 00010001
~ 00101101
~ 11000011

2. Phép toán Bitwise trên các số

Các ngôn ngữ khác nhau có thể có nhiều kiểu dữ liệu để biểu diễn số.

  • Javabyte, short, int, long, double.
  • C#: byte, sbyte, short, ushort, int, uint, long, ulong, float, double
  • Javascriptdouble
  • …..

Javascript lưu trữ các số như là các số chấm động 64 bit (64 bits floating point numbers). Nhưng các phép toán bitwise được thực hiện trên các số nguyên 32 bit. Các ngôn ngữ khác như Java, C#,.. các phép toán bitwise cũng được thực hiện trên các số nguyên 32 bit.Vì vậy trước khi thực hiện phép toán bitwise với các số bạn phải chuyển đổi mỗi số thành một dẫy 32 số nhị phân.

Base 10Base 232 bits
510100000000000000000000000000000101
2181101101000000000000000000000000011011010

Trong Javascript phương thức toString(base) giúp bạn chuyển một số bất kỳ từ hệ cơ số 10 (base 10) sang hệ cơ số khác.toString-base-example.js (Javascript)?

let a = 8;
 
 
// Base 2 string.
console.log( a.toString(2) );// 1000
 
// Base 8 string
console.log( a.toString(8) ); // 10
 
// Base 16 string
console.log( a.toString(16) ); // 8
 
 
let b = 218;
 
 
// Base 2 string.
console.log( b.toString(2) );// 11011010
 
// Base 8 string
console.log( b.toString(8) ); // 332
 
// Base 16 string
console.log( b.toString(16) ); // da

Ví dụ:

DecimalBinary
500000000000000000000000000000101
100000000000000000000000000000001
5 & 1 = 100000000000000000000000000000001
5 | 1  = 500000000000000000000000000000101
5 ^ 1  = 400000000000000000000000000000100
~ 5    = -611111111111111111111111111111010

Chú ý: Trong 32 bitbit đầu tiên được sử dụng để xác định dấu (sign) của số, nếu bit này là 1 tương ứng với dấu trừ ( – ), nếu bit này là 0 tương ứng với dấu cộng ( + )

Bitwise Left Shift (<<)
DecimalBinary
500000000000000000000000000000101
5 << 1  = 1000000000000000000000000000001010
5 << 2  = 2000000000000000000000000000010100

Toán tử Bitwise Left Shift ( << ) có thể làm thay đổi dấu (sign) của số.

(Javascript code)

console.log( 1073741824 << 1); // -2147483648
 
console.log( 2684354560 << 1); // 1073741824
Bitwise Right Shift (>>)  [Unsigned Right Shift]
DecimalBinary
2900000000000000000000000000011101
29 >> 1  = 1400000000000000000000000000001110
29 >> 2  = 700000000000000000000000000000111

Toán tử Bitwise Right Shift ( >> ) không làm thay đổi dấu của số, vì bit đầu tiên không bị di chuyển.

Bitwise Right Shift (>>>) [Zero fill right Shift]

Toán tử Bitwise Right Shift ( >>> ) có thể làm thay đổi dấu của số.

(Javascript Code)

console.log( -1073741824 >>> 1); // 1610612736
 
console.log( 1073741824 >>> 1); // 536870912

3. Bitwise để làm gì?

Các phép tính bitwise được hỗ trợ trực tiếp bởi bộ xử lý (processor) của máy tính nên nó thực hiện rất nhanh. Dưới đây tôi liệt kê một vài ví dụ sử dụng các phép toán này.Sử dụng các phép toán bitwise trên các String (characters) trên các ngôn ngữ Java, C#, C/C++ … Chú ý: một vài ngôn ngữ như Javascript không hỗ trợ phép toán bitwise với kiểu String.Chuyển đổi một chữ hoa (Uppercase) sang chữ thường (Lowercase):

// Rule: x | ' '
 
('A' | ' ') ==> 'a'
('B' | ' ') ==> 'b'
 
('a' | ' ') => 'a'

Chuyển đổi chữ thường (Lowercase) sang chữ hoa (Uppercase):

// Rule: x & '_'
 
 
('a' & '_') ==> 'A'
('b' & '_') ==> 'B'
 
('A' & '_') ==> 'A'

Đảo ngược chữ hoa thành chữ thường, chữ thường thành chữ hoa:

// Rule: x ^ ' '
  
('a' ^ ' ') ==> 'A'
('A' ^ ' ') ==> 'a'

Xem vị trí các chữ cái Latin (Chỉ áp dụng cho chữ hoa)

// Rule:  x & '?'
 
'A' & '?'  ==> 1
'B' & '?'  ==> 2
...
'Z' & '?'  ==> 26
 
// Rule:  x ^ '@'
 
 
'A' ^ '@'  ==> 1
'B' ^ '@'  ==> 2
...
'Z' ^ '@'  ==> 26

Xem vị trí các chữ cái Latin (Chỉ áp dụng cho chữ thường)

// Rule:  x ^ '`'
 
 
'a' ^ '`'  ==> 1
'b' ^ '`'  ==> 2
...
'z' ^ '`'  ==> 26
 
// '`' : binary ( 1100000 ), hex('60'),  chr(96)

Xem vị trí các chữ cái Latin, áp dụng cho cả chữ hoa và chữ thường:

// Rule:  x & '\u001F'
 
'A' & '\u001F'  ==> 1
'B' & '\u001F'  ==> 2
...
'Z' & '\u001F'  ==> 26
 
'A' & '\u001F'  ==> 1
'B' & '\u001F'  ==> 2
...
'Z' & '\u001F'  ==> 26
0

Leave a Reply

Your email address will not be published. Required fields are marked *