gpt4 book ai didi

无法完成国际象棋 table 上马的所有可能走法

转载 作者:行者123 更新时间:2023-11-30 15:27:30 26 4
gpt4 key购买 nike

更新:非常感谢 M Oehm 的精彩回答,对我帮助很大。 struct pos move 确实很有帮助,类里面还没学过。我正在研究我的代码的完整解决方案,将您的代码添加为程序骨架上的骨头。已经修复了更新 fila 和 columna 的问题,随机选择以及从 0 到 7 的切换(没有“”)的问题,因为它们不是您和 davidc 指出的字符。我的程序仍然存在一些问题,在此处发布完全可操作的程序之前我正在解决这些问题。如果今天不更新,我明天会更新代码。感谢大家的评论和解决方案,感谢 M oehm 花时间做出这个精彩的答案。
---------------------------------------------------------- -------------------------------------------------- ------------------------------------------------
更新2:完成了,对M Oehm代码做了一些小改动,我没有手动放置马的第一个位置,而是使用了之前的PosicionCaballo()。不得不删除 MoverCaballo() 的代码,该代码有一个带有 8 个可能移动的 Switch,这是由随机数设置的,因为我无法使其工作(我猜主要问题是那部分,因为已经一团糟了)。

现在包含以下代码的程序应该询问用户马的初始位置,之后屏幕将打印一个 10x10 的表格,其中填充 0(空闲空间),然后用 1 填充(取马随机移动的空格),当它完成时,会显示一条消息,说明它采取了多少个位置。

COORD cxy;
#define posicion(x,y) {(cxy.X)= (x);(cxy.Y)= (y); SetConsoleCursorPosition((GetStdHandle(STD_OUTPUT_HANDLE)), (cxy) );}

int ajedrez[10][10];
int fila, columna;

void GenerarTablero(int m[10][10]){
int i, j;
for (i = 0; i < 10; i++){
for (j = 0; j < 10; j++){
m[i][j] = 0;
}
}
}

GenerTablero 制作棋盘并用 0 填充它。
全局是 ajedrez[10][10]
的 fila(行)和 columna(列)部分ajedrez[10][10] 是 10x10 尺寸的国际象棋 table 。

void PosicionCaballo(int m[10][10]){
printf("Fila: ");
scanf_s("%d", &fila);
printf("Columna: ");
scanf_s("%d", &columna);
printf("\n");

m[fila][columna] = 2;
system("cls");

}

PosicionCaballo 确实会询问用户马的初始位置并将马放在 table 上。
示例:行:5 列:5

int horse(int y, int x)
{
int visited[SIZE][SIZE] = { { 0 } };
int count = 0;

if (on_board(y, x) == 0) return -1;

/* Set starting position */
visited[y][x] = 1;

while (1) { /* Infinite loop - must use break */
int poss[8]; /* Possible moves */
int nposs = 0; /* Actual length of poss */
int i, k = 1;

for (i = 0; i < 8; i++) {
int xx = x + moves[i].x;
int yy = y + moves[i].y;

if (on_board(yy, xx) && visited[yy][xx] == 0) {
poss[nposs++] = i;
}
}

/* No more valid moves: return */
if (nposs == 0){
posicion(0, 11);
printf("El tablero se ha bloqueado con ");
return count;
}

/* pick one of the valid moves */
i = poss[rand() % nposs];
x = x + moves[i].x;
y = y + moves[i].y;

/* update horse's position */
visited[y][x] = 1;
count++;

/* print position */

posicion(y, x);
printf("1");

}

return -1; /* Should never be reached */
}

void MostrarMapa(int m[10][10]){
int i, j;
for (i = 0; i < 10; i++){
for (j = 0; j < 10; j++){
printf("%d", ajedrez[i][j]);
}
printf("\n");
}
}

MostrarMapa 仅在屏幕上打印棋盘。

int main(void){

int n;

srand(time(NULL));
GenerarTablero(ajedrez);
PosicionCaballo(ajedrez);
MostrarMapa(ajedrez);
n = horse(fila, columna);
posicion(31, 11);
printf("%d movimientos\n", n);



getch();
return 0;
}

然后是我的主要部分,我正在使用上面提到的所有功能。
提前非常感谢你们的帮助:)。

最佳答案

我猜你的任务是找到一条访问所有方 block 的有效路径。您的代码尝试找到一个随机路径。

您的代码有几个错误:

  • 测试 ajedrez[fila - 2][columna - 1] 时,不会检查是 fila - 2 还是 columna - 1 code> 是棋盘上真正有效的索引。如果您访问无效索引(-1 或 11),则会调用未定义的行为。
  • 您不更新 filacolumna,即:您不移动您的马。
  • 您覆盖了棋盘两次。这不是一个错误,但您的代码不应该承担双重职责。
  • 您的随机选择已被破坏。您有八种可能的移动方式,因此您需要 rand() % 8,它会生成从 0 到 7 的数字。(David 已经在评论中指出了这一点。)
  • 您的大小写标签是字符常量,而不是数字。使用case 0:,而不是case '0':
  • 您只需跳过无效的 Action 。当不再有有效的移动时,这将导致无限循环。您应该检查此情况,如果发生则终止循环。
  • 据我了解,“posicion”宏只是为了显示马在哪里。也许您现在应该跳过它,只打印新坐标,这不是那么漂亮,但很简单。

您的八个开关案例显示了另一个缺陷:您有相同的重复代码八次。唯一的区别是跳跃模式。这样的设置适合​​于编写一个传递行和列距离进行跳转的函数,或者使用可能的跳转模式数组。

您的代码应该为每次移动执行类似的操作:

  • 循环所有八种跳跃模式。如果马会跳下棋盘或者如果马会访问已经访问过的图 block ,则跳过这种可能性。否则,将移动添加到辅助数组中。
  • 如果可能性为零,则终止循环 - 马无处可去。
  • 选择一个有效的 Action 。
  • 移动马,标记当前访问过的图 block 。
  • 如果需要,报告跳转:打印新位置或放置光标,等等。

下面是一个使用跳转模式数组的示例实现。它将给出一条随机路径。您可以根据您的问题调整此代码。

#include <stdlib.h>
#include <stdio.h>
#include <time.h> /* for time() */

#define SIZE 10 /* Fixed board size */

struct pos {
int x, y;
};

struct pos moves[8] = { /* Jump patterns */
{1, 2},
{2, 1},
{2, -1},
{1, -2},
{-1, -2},
{-2, -1},
{-2, 1},
{-1, 2}
};

/*
* Is position (y, x) a valid board coordinate?
*/
int on_board(int y, int x)
{
if (x < 0 || x >= SIZE) return 0;
if (y < 0 || y >= SIZE) return 0;
return 1;
}

/*
* Move the horse randomly, starting from (y, x). Print the
* visited fields and return the number of moves made or
* -1 if an error occurs.
*/
int horse(int y, int x)
{
int visited[SIZE][SIZE] = {{0}};
int count = 0;

if (on_board(y, x) == 0) return -1;

/* Set starting position */
visited[y][x] = 1;
printf("%c%d, ", 'A' + y, x + 1);

while (1) { /* Infinite loop - must use break */
int poss[8]; /* Possible moves */
int nposs = 0; /* Actual length of poss */
int i;

for (i = 0; i < 8; i++) {
int xx = x + moves[i].x;
int yy = y + moves[i].y;

if (on_board(yy, xx) && visited[yy][xx] == 0) {
poss[nposs++] = i;
}
}

/* No more valid moves: return */
if (nposs == 0){
printf("whoa!\n");
return count;
}

/* pick one of the valid moves */
i = poss[rand() % nposs];
x = x + moves[i].x;
y = y + moves[i].y;

/* update horse's position */
visited[y][x] = 1;
count++;

/* print position */
printf("%c%d, ", 'A' + y, x + 1);
}

return -1; /* Should never be reached */
}

int main()
{
int n;

srand(time(NULL));

n = horse(3, 6);
printf("%d moves\n", n);

return 0;
}

关于无法完成国际象棋 table 上马的所有可能走法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26956945/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com