走过的元素,用大写英文字母A-Z按顺序代替,运行出来乱七八糟的,斜着走,还跳2步。觉得自己写的很冗长,还没实现功能。
#include
#include
#include
#define RAW 10
#define COL 10
#define DIREC 4
int main(void)
{
char Checkerboard[RAW][COL],Letter[26];
int i=0,j=0,direction,k=1;
for(i=0;i<RAW;i++){
for(j=0;j<COL;j++)
Checkerboard[i][j]='.';
}
Letter[0]='A';
for(i=1;i<26;i++)
Letter[i]=Letter[i-1]+1;//26字母存入数组
srand((unsigned)time(NULL));
i=rand()%RAW;//余数0,1,2,3.....9
j=rand()%COL;//余数0,1,2,3.....9
Checkerboard[i][j]=Letter[0];//确定棋盘上第一个字母A的位置
while(Checkerboard[i+1][j]=='.'||Checkerboard[i-1][j]=='.'||Checkerboard[i][j+1]=='.' ||Checkerboard[i][j-1]=='.'){
direction=rand() % DIREC;//余数0,1,2,3代表方向
switch(direction){
case 0:
i--;//上移
if((i<10 && i>=0) && Checkerboard[i][j]=='.' ){
Checkerboard[i][j]=Letter[k];
k++;
break;
}
else
break;
case 1:
i++;//下移
if((i<10 && i>=0) && Checkerboard[i][j]=='.' ){
Checkerboard[i][j]=Letter[k];
k++;
break;
}
else
break;
case 2:
j--;//左移
if((j<10 && j>=0) && Checkerboard[i][j]=='.' ){
Checkerboard[i][j]=Letter[k];
k++;
break;
}
else
break;
case 3:
j++;//右移
if((j<10 && j>=0) && Checkerboard[i][j]=='.' ){
Checkerboard[i][j]=Letter[k];
k++;
break;
}
else
break;
}
}
for(i=0;i<RAW;i++){
for(j=0;j<COL;j++)
printf(" %c",Checkerboard[i][j]);
printf("\n");
}
return 0;
}
再看一下这个
#include <stdio.h>
#include<stdlib.h>
#include <time.h>
#define RAW 10
#define COL 10
#define DIREC 4
int main(void) {
char Checkerboard[RAW][COL], Letter[26];
int i = 0, j = 0, direction, k = 0;
for (i = 0; i < RAW; i++) {
for (j = 0; j < COL; j++)
Checkerboard[i][j] = '.';
}
// Letter[0] = 'A';
for (i = 0; i < 26; i++)
Letter[i] = 'A' + i;
srand((unsigned) time(NULL));
i = rand() % RAW;//余数0,1,2,3.....9
j = rand() % COL;//余数0,1,2,3.....9
Checkerboard[i][j] = Letter[0];//确定棋盘上第一个字母A的位置
k = 1;
while (k < 26) {
if (!((i < RAW - 1 && Checkerboard[i + 1][j] == '.') ||
(i > 0 && Checkerboard[i - 1][j] == '.') ||
(j < COL - 1 && Checkerboard[i][j + 1] == '.') ||
(j > 0 && Checkerboard[i][j - 1] == '.'))) {
//上下左右没有能走的了,就结束while循环
break;
}
direction = rand() % DIREC;//余数0,1,2,3代表方向
switch (direction) {
case 0:
if (i > 0 && Checkerboard[i - 1][j] == '.') {
Checkerboard[i - 1][j] = Letter[k];
k++;
i--;//上移
}
break;
case 1:
if (i < RAW - 1 && Checkerboard[i + 1][j] == '.') {
Checkerboard[i + 1][j] = Letter[k];
k++;
i++;//下移
}
break;
case 2:
if (j > 0 && Checkerboard[i][j - 1] == '.') {
Checkerboard[i][j - 1] = Letter[k];
k++;
j--;//左移
}
break;
case 3:
if (j < COL - 1 && Checkerboard[i][j + 1] == '.') {
Checkerboard[i][j + 1] = Letter[k];
k++;
j++;//右移
}
break;
}
}
for (i = 0; i < RAW; i++) {
for (j = 0; j < COL; j++)
printf(" %c", Checkerboard[i][j]);
printf("\n");
}
return 0;
}
#include
#include
#include
#define NUM_X 10 //这四条略微多余,可以不用
#define NUM_Y 10
#define TRUE 1
#define FALSE 0
int main() {
int walk[NUM_X][NUM_Y] = {0};
char eng[26] =
{'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'};
int i, j,k = 0, count = 0, up, down, left, right;
int num_x,num_y,num_location;
up = down = left = right = 5; //因为上下左右是用0,1,2,3来表示,这些变量存储一次值以后,下次就不用再比较了,当然,结束以后要还原 srand((unsigned)time(NULL)); //设置种子数在这里!!
我没有进行debug,但是能看出来有几个问题。
1.先教你一个小技巧,在debug的时候先固定起点好了,要不然每次起点都不一样debug找到问题可能慢
2.while循环没有判断越界问题。你的while判断是说当我现在的位置上下左右至少一个方向还能走。可是如果当前位置在边界上,比如i=0,那判断的时候checkboard[i-1][j]就越界了,所以while循环要加条件
3.switch处理不对。每个case你是说如果这个方向能走的话怎么着,那不能走的话呢,你就不忘这个方向走,可是你的i++,i--,j++,j--已经做过了,当前位置不对了。所以i++ -- j++ --这四句应该在if成立里面做
走过的元素用大写字母代替,元素终究都会被覆盖,学习算法中...
while ((i < RAW - 1 && Checkerboard[i + 1][j] == '.') || (i > 0 && Checkerboard[i - 1][j] == '.') || (j < COL - 1 && Checkerboard[i][j + 1] == '.') || (j > 0 && Checkerboard[i][j - 1] == '.') && k < 26) { direction = rand() % DIREC;//余数0,1,2,3代表方向 switch (direction) { case 0: if (i > 0 && Checkerboard[i - 1][j] == '.') { Checkerboard[i-1][j] = Letter[k]; k++; i--;//上移 break; } else break; case 1: if (i < RAW - 1 && Checkerboard[i + 1][j] == '.') { Checkerboard[i+1][j] = Letter[k]; k++; i++;//下移 break; } else break; case 2: if (j > 0 && Checkerboard[i][j - 1] == '.') { Checkerboard[i][j-1] = Letter[k]; k++; j--;//左移 break; } else break; case 3: if (j < COL - 1 && Checkerboard[i][j + 1] == '.') { Checkerboard[i][j+1] = Letter[k]; k++; j++;//右移 break; } else break; } }
#include
#include
#include
#define RAW 10
#define COL 10
#define DIREC 4
int main(void) {
char Checkerboard[RAW][COL], Letter[26];
int i = 0, j = 0, direction, k = 1;
for (i = 0; i < RAW; i++) {
for (j = 0; j < COL; j++)
Checkerboard[i][j] = '.';
}
Letter[0] = 'A';
for (i = 1; i < 26; i++)
Letter[i] = Letter[i - 1] + 1;//26字母存入数组
srand((unsigned) time(NULL));
i = rand() % RAW;//余数0,1,2,3.....9
j = rand() % COL;//余数0,1,2,3.....9
Checkerboard[i][j] = Letter[0];//确定棋盘上第一个字母A的位置
while ((i < RAW - 1 && Checkerboard[i + 1][j] == '.') ||
(i > 0 && Checkerboard[i - 1][j] == '.') ||
(j < COL - 1 && Checkerboard[i][j + 1] == '.') ||
(j > 0 && Checkerboard[i][j - 1] == '.') && k < 26) {
direction = rand() % DIREC;//余数0,1,2,3代表方向
switch (direction) {
case 0:
if (i > 0 && Checkerboard[i - 1][j] == '.') {
Checkerboard[i-1][j] = Letter[k];
k++;
i--;//上移
break;
} else
break;
case 1:
if (i < RAW - 1 && Checkerboard[i + 1][j] == '.') {
Checkerboard[i+1][j] = Letter[k];
k++;
i++;//下移
break;
} else
break;
case 2:
if (j > 0 && Checkerboard[i][j - 1] == '.') {
Checkerboard[i][j-1] = Letter[k];
k++;
j--;//左移
break;
} else
break;
case 3:
if (j < COL - 1 && Checkerboard[i][j + 1] == '.') {
Checkerboard[i][j+1] = Letter[k];
k++;
j++;//右移
break;
} else
break;
}
}
for (i = 0; i < RAW; i++) {
for (j = 0; j < COL; j++)
printf(" %c", Checkerboard[i][j]);
printf("\n");
}
return 0;
}
首先得知道围棋的规则,如果再加个机器人对战的算法就杠杠的了
这个while(Checkerboard[i+1][j]=='.'||Checkerboard[i-1][j]=='.'||Checkerboard[i][j+1]=='.' ||Checkerboard[i][j-1]=='.')和上边的for循环导致你说的现象。
while里面条件不对,只有当这个点四周都没有被走过才作为起始点。
应该对i,j这个点的周围4个点进行判断。然后再产生随机数,去移动点就行了。
bool bMovable[4] = {false};// 0 上 1下 2左 3右
int nMovableNum = 0;
int i = 0// 循环用
if(Checkerboard[i-1][j]=='.' && i-1 >=0)// 判断当前点上方是否可以落子
bMovable[0] = true;
else
bMovable[0] = false;
if(Checkerboard[i+1][j]=='.' && i+1 <=9)// 判断当前点下方是否可以落子
bMovable[1] = true;
else
bMovable[1] = false;
if(Checkerboard[i][j-1]=='.' && j-1 >=0)// 判断当前点左方是否可以落子
bMovable[2] = true;
else
bMovable[2] = false;
if(Checkerboard[i][j+1]=='.' && j+1 <=9)// 判断当前点右方是否可以落子
bMovable[3] = true;
else
bMovable[3] = false;
for (i = 0; i<4; ++i)
{
if(bMovable[i])
++nMovableNum;
}
if(nMovableNum == 0)/// 无路可走
/// 结束或者重开 看你的逻辑 我这里就return了
return;
int nDirect = rand()%nMovableNum;
for (i = 0; i<4; ++i)
{
if(bMovable[i])
{
--nDirect;
if(nDirect < 0)
break;
}
}
switch(i)/// 根据上下左右进行相应的移动
{
case 0: /// 上
Checkerboard[i-1][j] = Letter[k];
break;
...
case 3:
Checkerboard[i][j+1] = Letter[k];
break;
}
这是我写的 你可以参考下
nMovableNum 需要再每次循环后重置。 应该能解决你的问题。
我这里隐含默认走过的就不再走了。
解决了请采纳哦,谢谢。
#include
#include
#include /*包含的所调用库函数的头文件*/
/*
*function: 在控制台指定的位置输出字符串
*参数:alphabet,输出的字符;startX、startY为控制台的X,Y坐标
*/
void printStr(char alphabet, int startX, int startY)
{
HANDLE hd;
COORD pos;
pos.X = startX;
pos.Y = startY;
hd = GetStdHandle(STD_OUTPUT_HANDLE); /*获取标准输出的句柄*/
SetConsoleCursorPosition(hd, pos); /*设置控制台光标输出的位置*/
printf("%c", alphabet);
}
int poshandle(char nextdir, char* pos_x, char* pos_y)
{
int ret = 0;
switch(nextdir)
{
case 0: //向上
*pos_y = *pos_y - 1;
if(*pos_y < 0)
{
*pos_y = *pos_y + 1;
ret = 0;
}
ret = 1;
break;
case 1: //向下
*pos_y = *pos_y + 1;
if(*pos_y > 9)
{
*pos_y = *pos_y - 1;
ret = 0;
}
ret = 1;
break;
case 2: //向左
*pos_x = *pos_x - 1;
if(*pos_x < 0)
{
*pos_x = *pos_x + 1;
ret = 0;
}
ret = 1;
break;
case 3: //向右
*pos_x = *pos_x + 1;
if(*pos_x > 9)
{
*pos_x = *pos_x - 1;
ret = 0;
}
ret = 1;
break;
default:
break;
}
return ret;
}
int main(int argc,char *argv[])
{
char showcontent;
char count = 30;
char x = 0, y = 0;
char nextdir = 0;
showcontent = '.';
srand( (unsigned)time( NULL ) );
for(x = 0; x < 10; x++){
for(y = 0; y < 10; y++)
{
printStr(showcontent, x,y);
}
}
x = rand()%10;
y = rand()%10;
showcontent = 'A';
while(count --)
{
printStr(showcontent, x,y);
nextdir = rand()% 4;
if(poshandle(nextdir, &x, &y) == 0)
continue;
showcontent++;
if(showcontent > 'Z')
showcontent = 'A';
getchar();
}
printStr('\0', 0, 10);
system("pause");
return 0;
}
楼主,我今天按照你的要求写了段程序,我自己调试没什么问题。供你参考,也欢迎大家指教。
我把这个题目整理了一篇博客,地址:http://blog.csdn.net/xikangsoon/article/details/79446518。
1.在初始化地图的时候,对边界(超出定义范围外的值进行赋值,比如全部是字母A),以空间增加换取减少一次边界值判断。
2.对四个方向确定x、y变化的数组。以便定义方向。
lstX[0] = 1
lstX[1] = -1
lstX[2] = 0
lstX[3] = 0
lstY[0] = 0
lstY[1] = 0
lstY[2] = 1
lstY[3] = -1
3.对不同case提炼一致性动作后可用如下语句代替
nNewX = lstX[direction] + nLastX
nNewY = lstY[direction] + nLastY
if (Checkerboard[nNewX][nNewY] == ‘.’)
{
Checkerboard[nNewX][nNewY] = Letter[k];
nLastX = nNewX
nLastY = nNewY
k++
}