Bitwise-OR vs Thêm cờ


16

Tôi đã thấy những người khác sử dụng Bitwise-OR để kết hợp các cờ trước đây:

#define RUN 0x01
#define JUMP 0x02
#define SHOOT 0x04

const byte madPerson = RUN | JUMP | SHOOT;

Đó cũng là cách tôi làm.

Nhưng tôi cũng đã thấy một số (không nhiều) kết hợp cờ bằng cách sử dụng bổ sung:

#define RUN 0x01
#define JUMP 0x02
#define SHOOT 0x04

const byte madPerson = RUN + JUMP + SHOOT;

Cái nào "dễ đọc" hơn? (Bạn nghĩ ai sẽ nhận ra nhiều người hơn?) Cách "chuẩn" để làm điều đó là gì? Bạn thích cái nào hơn?


Đây là một câu hỏi SO. Xem xét sử dụng một cái gì đó giống như 1<<0, 1<<1, 1<<2, và vân vân. Khi bạn có nhiều cờ, nó sẽ trở nên dễ đọc hơn, dễ bảo trì hơn, ít bị lỗi hơn. Ví dụ, nếu bạn đang đóng gói tất cả 64 bit của int 64 bit, bạn thực sự muốn tránh lỗi chính tả :) Cách bạn thể 1hiện cũng rất quan trọng. Đối với một số nguyên 64 bit trong VS2010 tôi nghĩ rằng nó là 1UI64, hoặc một cái gì đó tương tự. Sử dụng sai loại có thể cắn bạn.
Công việc

3
@Job: Không phải là một câu hỏi StackOverflow, bởi vì nó hỏi về khả năng đọc, khả năng nhận biết, sở thích và thực tiễn tốt nhất. Không có câu trả lời khách quan duy nhất cho nó; nó thuộc về nơi này
Macneil

Câu trả lời:


34

Bitwise-HOẶC.

Ngoài ra là nguy hiểm.

Hãy xem xét một ví dụ trong đó một tên cướp là một người, và một tên cướp tức giận là một tên cướp biết nói và bắn. Sau đó, bạn quyết định tất cả kẻ cướp nên bắn, nhưng bạn đã quên mất định nghĩa tên cướp tức giận và không xóa cờ bắn của nó.

#define PERSON 1 << 0
#define SPEAKS 1 << 1
#define SHOOTS 1 << 2
#define INVINCIBLE 1 << 3
const byte bandit = PERSON | SHOOTS;                    // 00000101
const byte angryBandit_add = bandit + SPEAKS + SHOOTS;  // 00001011 error
const byte angryBandit_or = bandit | SPEAKS | SHOOTS;   // 00000111 ok

Nếu bạn đã sử dụng angryBandit_addtrò chơi của mình thì bây giờ sẽ có lỗi logic bối rối khi có những tên cướp tức giận không thể bắn hoặc bị giết.

Nếu bạn sử dụng angryBandit_ortồi tệ nhất bạn có là một dự phòng | SHOOTS.

Vì những lý do tương tự, bitwise KHÔNG an toàn hơn phép trừ để xóa cờ.


11

bitwise-HOẶC truyền đạt ý định rõ ràng hơn

Ngoài ra, bitwise-OR sẽ hiệu quả hơn


+1 thực sự tôi cũng nghĩ rằng HOẶC làm rõ hơn rằng đó là các cờ, nhưng liên quan đến hiệu quả có các ngôn ngữ mà hoạt động bitwise chậm, ví dụ JavaScript tất cả các số là 64 toán tử bit bit toán tử cần thực hiện chuyển đổi ngầm định trên các ngôn ngữ đó.
Ivo Wetzel

1
Lấy ví dụ của OP, tôi không nghĩ một dòng OR hoặc bổ sung sẽ ảnh hưởng xấu đến tốc độ thực hiện của chương trình.
Tin Man

1
@Greg: đặc biệt vì tính toán trong ví dụ đó sẽ được thực hiện tại thời điểm biên dịch. :-)
Carson63000

Ngoài việc truyền đạt ý định, khá phổ biến để thấy điều này bằng nhiều ngôn ngữ bao gồm nhưng không giới hạn ở ADA, C #, Java ...
Ken Henderson

2
"Nên" là một từ rất lớn trong kinh doanh này. Mặc dù rất khó có khả năng bạn sẽ gặp phải vấn đề này ngày hôm nay, tôi có những ký ức rất rõ ràng khi làm việc với bộ xử lý không có hướng dẫn OR-bit. Bạn có thể bitwise-AND trong một hướng dẫn, và bạn có thể bitwise-XOR trong một lệnh, nhưng bitwise-OR lấy hai: bitwise ngay lập tức-VÀ để tắt bit, và bit X-bit ngay lập tức để bổ sung cho bit mới được xóa , mà tất nhiên thiết lập nó.
John R. Strohm
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.