Discuz! Board

 找回密碼
 立即註冊
搜索
熱搜: 活動 交友 discuz
查看: 124|回復: 0
打印 上一主題 下一主題

使用位字段和掩码寫一個國際象棋遊戲

[複製鏈接]

1834

主題

1834

帖子

5538

積分

管理員

Rank: 9Rank: 9Rank: 9

積分
5538
跳轉到指定樓層
樓主
發表於 2024-4-22 16:17:39 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
假如你在用 C 說话寫一個國際象棋遊戲。追踪棋盘上棋子的一種法子是界說一個布局,该布局界說了棋盘上每一個可能的棋子及其色彩,是以每一個格子都包括该布局中的一個元素。比方,你可以将布局界說成下面如许:

  1. struct chess_pc {
  2. int piece;
  3. int is_black;
  4. }
複製代碼

有了這個数据布局,你的步伐就會晓得每一個格子里是甚麼棋子及棋子的色彩。你可以快速辨認出棋子是兵、車、马、象、後仍是王,和棋子是黑仍是白。可是,有一種更直接的法子来跟踪這些信息,同時只用音波拉皮, 更少的数据和内存。與為棋盘上的每一個方格存储hoya,两個 int 值的布局分歧,咱们可以存储单個 int 值,并利用二進制位字段和掩码来標識每一個方格中的棋子和色彩。

當利用位字段暗示数据時,咱们最仿佛计较機同样思虑。讓咱们從列出可能的棋子起頭,并為每一個棋子分派一個数字。讓咱们進入下一個步调,用二進制暗示這個数字,也就是依照计较機追踪它的方法。记着,二進制数是由比特構成的,比特要末是 0,要末是 1。

要列出一個棋盘上的所有棋子,咱们只必要三個比特從右到左挨次代表值 一、2 和 4。比方,数字 6 是二進制的 110。6 的二進制暗示中的其他所有位都是 0。

一個聪慧一點的法子:咱们可使用那些分外的老是為零的比特来跟踪一個棋子是黑仍是白。咱们可使用数字 8(二進制 00001000)来暗示棋子是不是為玄色。若是這一名是 1,則代表该棋子是玄色;若是是 0,則代表该棋子是白色。這被称為位字段,稍後咱们可小琉球三天兩夜包棟民宿,使用二進制掩码将其掏出。

要编寫一個利用位字段和掩码的國際象棋步伐,咱们可以從如下界說起頭:

  1. /* 棋子 */
  2. #define EMPTY 0   // 空
  3. #define PAWN 1    // 兵
  4. #define ROOK 2    // 車
  5. #define KNIGHT 3  // 马
  6. #define BISHOP 4  // 象
  7. #define QUEEN 5   // 後
  8. #define KING 6    // 王

  9. /* 棋色 */
  10. #define BLACK 8   // 黑
  11. #define WHITE 0   // 白

  12. /* 掩码 */
  13. #define PIECE 7
複製代碼

當你為一個棋格赋值時,好比初始化棋盘,你可以赋一個 int 類型的值来跟踪棋子及其色彩。比方,要在棋盘的 0,0 位置存储棋子黑車,你可使用下面的代码:

  1. int board[8][8];
  2. ..
  3. board[0][0] = BLACK | ROOK;
複製代碼

| 是二進制“或”(OR)操作符,這象征着计较機将归并两個数字的比特。對付每一個比特的位置,若是肆意一個数字的比特為 1,该位置比特的成果也是 寵物商品, 1。BLACK 的值(8,即二進制下的 00001000)和 ROOK 的值(2,即二進制下的 00000010)的二進制或成果是二進制下的 00001010,即 10:

  1. 00001000 = 8
  2. OR 00000010 = 2
  3. ________
  4. 00001010 = 10
複製代碼

雷同地,要在棋盘的 6,0 位置存储一個白色兵,你可以如许做:

  1. board[6][0] = WHITE | PAWN;
複製代碼

如许存储的值就是 WHITE(0)和 PAWN(1)的二進制或的成果,也便是 1。

  1. 00000000 = 0
  2. OR 00000001 = 1
  3. ________
  4. 00000001 = 1
複製代碼

鄙人棋進程中,步伐必要晓得棋格中的棋子和它的色彩。咱们可使用二進制掩码来分手這部門。

举個例子,步伐可能必要晓得棋局中棋盘上特定棋格的内容,比方位於 board[5][3] 的数组元素。這個是甚麼棋子,是黑的仍是白的?為了辨認棋子,利用二進制“與”(AND)操作符将元素的值與掩码 PIECE 連系起来:

  1. int board[8][8];
  2. int piece;
  3. ..
  4. piece = board[5][3] & PIECE;
複製代碼

二進制“與”(AND)操作符(&)将两個二進制值連系,如许對付肆意位,若是两個数字中的阿谁位都是 1,那末成果也是 1。比方,若是 board[5][3] 的值是 11(二進制下的 00001011),那末 11 和 掩码 PIECE(7,二進制下的 00000111)二進制與的成果為二進制下的 00000011,也即 3。頭髮增長液,這代表马,马的值是 3。

  1. 00001011 = 11
  2. AND 00000111 = 7
  3. ________
  4. 00000011 = 3
複製代碼

解析棋子的色彩是一個简略的事變,只必要将棋子的值與 BLACK 位字段举行二進制與操作。好比,你可以寫一個名為 is_black 的函数来肯定棋子是黑仍是白:

  1. int is_black(int piece)
  2. {
  3. return (piece & BLACK);
  4. }
複製代碼

之以是可以如许,是由於 BLACK 的值為 8(二進制下的 00001000)。在 C 說话中,任何非零值都被視為 True,零老是 False。以是若是 5,3 處的棋子是玄色的,則 is_black(board[5][3]) 返回 True 值(8);若是是白色的,則返回 False 值(0)。

利用位字段和掩码是不利用布局组合数据的經常使用法子。它们值得被步伐员保藏到“东西包”中。固然数据布局對付必要跟踪相干数据的有序编程是一種有價值的东西,可是利用零丁的元夙来跟踪单個的開或闭值(比方棋子的色彩)的效力较低。在這些环境下,可以斟酌利用位字段和掩码来更高效地组合数据。

本文瘦身產品,利用 CC BY-SA 4.0 國際协定 举行允许,接待 依照协定划定 轉载。

原文: Write a chess game using bit-fields and masks

首發:利用位字段和掩码寫一個國際象棋遊戲 @ Linux中國
回復

使用道具 舉報

您需要登錄後才可以回帖 登錄 | 立即註冊

本版積分規則

Archiver|手機版|小黑屋|台灣運動彩券投注交流論壇  

台灣運彩官網運彩好朋友日本職棒比分, 法網直播線上直播王運動世界, 中華職棒即時比分, ptt網頁版, 中華職棒ptt, 日本職棒比分, 富遊娛樂城, 捕魚機遊戲, 運彩場中, 九州娛樂城, 歐冠杯決賽, 歐冠盃決賽, 最新娛樂城, 歐冠盃歐冠盃決賽歐冠盃LEO娛樂財神娛樂財神娛樂城娛樂城註冊送娛樂城體驗金線上娛樂線上娛樂城台灣運動彩券首頁運動彩場中投注場中投注時間表台灣運彩足球賠率運彩場中運動彩券單場運彩單場場中投注時刻表台灣運彩場中運動彩券場中場中投注表

GMT+8, 2024-11-22 09:51 , Processed in 0.017069 second(s), 4 queries , File On.

Powered by Discuz! X3.3

© 2001-2017 Comsenz Inc.

快速回復 返回頂部 返回列表