• 【gpt实践】同时让chatgpt和claude开发俄罗斯方块


    最近chatgpt和claude都在使用,其实大部分日常使用场景表现都没有相差太多,想搞一个有趣的小实验,如果同时让chatgpt和claude开发俄罗斯方块谁会表现的更好呢,说干就干!

    claude稳定账号获取
    prompt

    我选择了用英文描述,毕竟英文数据库更丰富,而且claude封禁比较严格,语言上也是小心翼翼

    prompt:I have few development experience, and I want to develope the game 'Tetris' totally basing on html5, css and javascript. I have a few requests: 1, we need a start button, 2, a scoreboard recording score 3, pop up gameover 4, full functionality of a complete Tetris game, their movement, collision detection, scoring, and clearing lines give me all the codes, that can run the game in the browse.

    我的开发经验不多,我想开发一款完全基于 html5、css 和 javascript 的 "俄罗斯方块 "游戏。我有几个要求: 1、我们需要一个开始按钮;2、一个记录得分的记分板;3、弹出式游戏结束界面;4、一个完整俄罗斯方块游戏的全部功能,包括移动、碰撞检测、得分和清线。

    chatgpt回答

    1. // Define variables and constants
    2. const canvas = document.getElementById('gameCanvas');
    3. const ctx = canvas.getContext('2d');
    4. const startButton = document.getElementById('startButton');
    5. const scoreboard = document.getElementById('score');
    6. const gameOver = document.getElementById('gameOver');
    7. let score = 0;
    8. let gameInterval;
    9. let gameOverFlag = false;
    10. // Define Tetris pieces and their colors
    11. const pieces = [
    12. [[1, 1, 1, 1]], // I
    13. [[1, 1, 1], [0, 1, 0]], // T
    14. [[1, 1, 0], [0, 1, 1]], // Z
    15. [[0, 1, 1], [1, 1, 0]], // S
    16. [[1, 1, 1], [0, 1, 0]], // L
    17. [[1, 1, 1], [1, 0, 0]], // J
    18. [[1, 1], [1, 1]], // O
    19. ];
    20. const colors = ['#00FFFF', '#FF00FF', '#FFA500', '#FFFF00', '#00FF00', '#0000FF', '#FF0000'];
    21. // Define functions for game logic (e.g., draw, move, rotate, check collision, etc.)
    22. // Implement game logic
    23. // Implement startGame function
    24. // Implement gameOver function
    25. // Implement key event listeners for controlling the game (e.g., arrow keys for movement)
    26. // Implement the main game loop
    27. // Implement functions for clearing lines, updating score, etc.
    28. // Implement collision detection and game over check
    29. // Implement rendering functions (e.g., drawPiece, drawBoard, etc.)
    30. // Implement functions for moving and rotating pieces
    31. // Implement functions for handling user input (e.g., start game, pause, resume, etc.)
    32. // Start the game when the start button is clicked
    33. startButton.addEventListener('click', startGame);

    考虑篇幅关系,忽略了html和css部分截图,文章最后会给出源码!!!

    可以看出chatgpt的做了一些方法定义,但是并没有实现。

    claude回答
    1. const canvas = document.getElementById('game-canvas');
    2. const ctx = canvas.getContext('2d');
    3. const scoreDisplay = document.getElementById('score');
    4. const startButton = document.getElementById('start-button');
    5. const gameOverMessage = document.getElementById('game-over-message');
    6. // Game constants
    7. const ROWS = 20;
    8. const COLS = 10;
    9. const BLOCK_SIZE = 20;
    10. const LINE_CLEAR_POINTS = 100;
    11. // Game state
    12. let board = [];
    13. let piece = null;
    14. let isGameOver = false;
    15. let isPlaying = false;
    16. let score = 0;
    17. // Tetromino shapes
    18. const shapes = [
    19. [
    20. [0, 0, 0, 0],
    21. [1, 1, 1, 1],
    22. [0, 0, 0, 0],
    23. [0, 0, 0, 0]
    24. ],
    25. [
    26. [1, 0, 0],
    27. [1, 1, 1],
    28. [0, 0, 0]
    29. ],
    30. [
    31. [0, 0, 1],
    32. [1, 1, 1],
    33. [0, 0, 0]
    34. ],
    35. [
    36. [1, 1, 0],
    37. [0, 1, 1],
    38. [0, 0, 0]
    39. ],
    40. [
    41. [0, 1, 1],
    42. [1, 1, 0],
    43. [0, 0, 0]
    44. ],
    45. [
    46. [1, 1],
    47. [1, 1]
    48. ],
    49. [
    50. [0, 1, 0],
    51. [1, 1, 1],
    52. [0, 0, 0]
    53. ]
    54. ];
    55. // Helper functions
    56. function drawBoard() {
    57. ctx.clearRect(0, 0, canvas.width, canvas.height);
    58. for (let row = 0; row < ROWS; row++) {
    59. for (let col = 0; col < COLS; col++) {
    60. if (board[row][col]) {
    61. ctx.fillStyle = 'yellow';
    62. ctx.fillRect(col * BLOCK_SIZE, row * BLOCK_SIZE, BLOCK_SIZE, BLOCK_SIZE);
    63. }
    64. }
    65. }
    66. if (piece) {
    67. drawPiece(piece.shape, piece.x, piece.y);
    68. }
    69. }
    70. function drawPiece(shape, x, y) {
    71. ctx.fillStyle = 'red';
    72. for (let row = 0; row < shape.length; row++) {
    73. for (let col = 0; col < shape[row].length; col++) {
    74. if (shape[row][col]) {
    75. ctx.fillRect((x + col) * BLOCK_SIZE, (y + row) * BLOCK_SIZE, BLOCK_SIZE, BLOCK_SIZE);
    76. }
    77. }
    78. }
    79. }
    80. function resetBoard() {
    81. board = Array.from({ length: ROWS }, () => Array(COLS).fill(0));
    82. }
    83. function randomPiece() {
    84. const randomIndex = Math.floor(Math.random() * shapes.length);
    85. return {
    86. shape: shapes[randomIndex],
    87. x: 3,
    88. y: 0
    89. };
    90. }
    91. function movePiece(direction) {
    92. if (!piece) return;
    93. const newX = piece.x + (direction === 'left' ? -1 : direction === 'right' ? 1 : 0);
    94. const newY = piece.y + (direction === 'down' ? 1 : 0);
    95. if (canMove(piece.shape, newX, newY)) {
    96. piece.x = newX;
    97. piece.y = newY;
    98. } else if (direction === 'down') {
    99. placePiece();
    100. clearLines();
    101. if (!isGameOver) {
    102. piece = randomPiece();
    103. }
    104. }
    105. drawBoard();
    106. }
    107. function canMove(shape, x, y) {
    108. for (let row = 0; row < shape.length; row++) {
    109. for (let col = 0; col < shape[row].length; col++) {
    110. if (shape[row][col]) {
    111. const newX = x + col;
    112. const newY = y + row;
    113. if (
    114. newX < 0 ||
    115. newX >= COLS ||
    116. newY >= ROWS ||
    117. (newY >= 0 && board[newY][newX])
    118. ) {
    119. return false;
    120. }
    121. }
    122. }
    123. }
    124. return true;
    125. }
    126. function placePiece() {
    127. if (!piece) return;
    128. for (let row = 0; row < piece.shape.length; row++) {
    129. for (let col = 0; col < piece.shape[row].length; col++) {
    130. if (piece.shape[row][col]) {
    131. board[piece.y + row][piece.x + col] = 1;
    132. }
    133. }
    134. }
    135. }
    136. function clearLines() {
    137. let linesCleared = 0;
    138. for (let row = ROWS - 1; row >= 0; row--) {
    139. let isFull = true;
    140. for (let col = 0; col < COLS; col++) {
    141. if (!board[row][col]) {
    142. isFull = false;
    143. break;
    144. }
    145. }
    146. if (isFull) {
    147. linesCleared++;
    148. for (let r = row; r > 0; r--) {
    149. for (let c = 0; c < COLS; c++) {
    150. board[r][c] = board[r - 1][c];
    151. }
    152. }
    153. for (let c = 0; c < COLS; c++) {
    154. board[0][c] = 0;
    155. }
    156. }
    157. }
    158. score += linesCleared * LINE_CLEAR_POINTS;
    159. scoreDisplay.textContent = `Score: ${score}`;
    160. }
    161. function rotatePiece() {
    162. if (!piece) return;
    163. const newShape = Array.from({ length: piece.shape[0].length }, () =>
    164. Array(piece.shape.length).fill(0)
    165. );
    166. for (let row = 0; row < piece.shape.length; row++) {
    167. for (let col = 0; col < piece.shape[row].length; col++) {
    168. newShape[col][piece.shape.length - 1 - row] = piece.shape[row][col];
    169. }
    170. }
    171. if (canMove(newShape, piece.x, piece.y)) {
    172. piece.shape = newShape;
    173. }
    174. drawBoard();
    175. }
    176. function isGameOverCheck() {
    177. for (let col = 0; col < COLS; col++) {
    178. if (board[0][col]) {
    179. isGameOver = true;
    180. gameOverMessage.classList.remove('hidden');
    181. break;
    182. }
    183. }
    184. }
    185. // Event listeners
    186. document.addEventListener('keydown', (event) => {
    187. if (!isPlaying) return;
    188. switch (event.code) {
    189. case 'ArrowLeft':
    190. movePiece('left');
    191. break;
    192. case 'ArrowRight':
    193. movePiece('right');
    194. break;
    195. case 'ArrowDown':
    196. movePiece('down');
    197. break;
    198. case 'ArrowUp':
    199. rotatePiece();
    200. break;
    201. }
    202. });
    203. startButton.addEventListener('click', () => {
    204. if (isPlaying) {
    205. isPlaying = false;
    206. startButton.textContent = 'Start';
    207. gameOverMessage.classList.add('hidden');
    208. } else {
    209. isPlaying = true;
    210. startButton.textContent = 'Pause';
    211. isGameOver = false;
    212. score = 0;
    213. scoreDisplay.textContent = `Score: ${score}`;
    214. resetBoard();
    215. piece = randomPiece();
    216. drawBoard();
    217. }
    218. });
    219. // Game loop
    220. function gameLoop() {
    221. if (!isPlaying) return;
    222. movePiece('down');
    223. isGameOverCheck();
    224. if (!isGameOver) {
    225. requestAnimationFrame(gameLoop);
    226. }
    227. }
    228. // Start the game
    229. resetBoard();
    230. piece = randomPiece();
    231. drawBoard();
    232. gameLoop();

    同样只贴出js部分的代码。可以看到claude给出了相对完善的js逻辑,所以我们直接选择用claude回答的代码进行调试,看看是否能正常在浏览器中运行。

    贴出代码:

    浏览器打开tetris运行效果:

    可以看到,点击开始后方块不会自动下落,需要手动按下,继续反馈优化:

    反馈完善功能

    prompt:I mean when the game starts without pressing the down button, the cube falls at a constant speed

    即当游戏开始时,方块保持匀速下落。

    1. const canvas = document.getElementById('game-canvas');
    2. const ctx = canvas.getContext('2d');
    3. const scoreDisplay = document.getElementById('score');
    4. const startButton = document.getElementById('start-button');
    5. const gameOverMessage = document.getElementById('game-over-message');
    6. // Game constants
    7. const ROWS = 20;
    8. const COLS = 10;
    9. const BLOCK_SIZE = 20;
    10. const LINE_CLEAR_POINTS = 100;
    11. const FALL_SPEED = 500; // Adjust this value to control the falling speed (in milliseconds)
    12. // Game state
    13. let board = [];
    14. let piece = null;
    15. let isGameOver = false;
    16. let isPlaying = false;
    17. let score = 0;
    18. let lastTime = 0;
    19. let fallInterval = null;
    20. // Tetromino shapes
    21. // ... (shapes array remains the same)
    22. // Helper functions
    23. // ... (drawBoard, drawPiece, resetBoard, randomPiece, movePiece, canMove, placePiece, clearLines, rotatePiece, isGameOverCheck functions remain the same)
    24. // Event listeners
    25. document.addEventListener('keydown', (event) => {
    26. if (!isPlaying) return;
    27. switch (event.code) {
    28. case 'ArrowLeft':
    29. movePiece('left');
    30. break;
    31. case 'ArrowRight':
    32. movePiece('right');
    33. break;
    34. case 'ArrowUp':
    35. rotatePiece();
    36. break;
    37. }
    38. });
    39. startButton.addEventListener('click', () => {
    40. if (isPlaying) {
    41. isPlaying = false;
    42. startButton.textContent = 'Start';
    43. gameOverMessage.classList.add('hidden');
    44. clearInterval(fallInterval); // Stop the automatic falling
    45. } else {
    46. isPlaying = true;
    47. startButton.textContent = 'Pause';
    48. isGameOver = false;
    49. score = 0;
    50. scoreDisplay.textContent = `Score: ${score}`;
    51. resetBoard();
    52. piece = randomPiece();
    53. drawBoard();
    54. lastTime = performance.now(); // Get the current time
    55. fallInterval = setInterval(gameLoop, FALL_SPEED); // Start the automatic falling
    56. }
    57. });
    58. // Game loop
    59. function gameLoop() {
    60. if (!isPlaying) return;
    61. const currentTime = performance.now();
    62. const deltaTime = currentTime - lastTime;
    63. if (deltaTime >= FALL_SPEED) {
    64. movePiece('down');
    65. isGameOverCheck();
    66. lastTime = currentTime;
    67. }
    68. if (!isGameOver) {
    69. requestAnimationFrame(gameLoop);
    70. } else {
    71. clearInterval(fallInterval); // Stop the automatic falling when the game is over
    72. }
    73. }
    74. // Start the game
    75. resetBoard();
    76. piece = randomPiece();
    77. drawBoard();

    可以看到claude会的的js代码里增加了方块下落的逻辑。点击开始后方块就能匀速下落

    当然后面还有几个小问题,比如按下键没有加速下落,方块无法移动到最右端,这些都通过反馈cluade得到了解决,最终能正常运行记分,效果如下:

    源码及claude导出文件

    https://github.com/JiangSanJie/gpt-practice/

    总结:

    claude稳定账号获取

    在本次俄罗斯方块的开发prompt中,claude回答相对完善,通过少量的反馈即可完成开发。当然其实chatgpt也能完成,但是需要prompt更加细致,可能针对回答的反馈会繁琐一些,这个感兴趣的读者可以去实验。我相信好的prompt会提高回答满意率!

  • 相关阅读:
    示例:【新学期、新Flag】与CSDN的故事
    AspNetCore开源中间件-VueRouterHistory
    linux系统安装 -----Centos 8 64位
    【C++】——类与对象引入和认识
    python基于PHP+MySQL的图书馆自习室预约占座系统
    A-level 物理实验题目
    用Python实现感知机学习算法及其对偶算法实验报告
    【七夕特别篇】七夕已至,让爱闪耀
    《面试求职系列》(三):如何写简历及求职技巧
    (四)详解工厂模式
  • 原文地址:https://blog.csdn.net/u012203062/article/details/136659556