字符游戏-智能蛇

一 我的Linux环境:Ubuntu
这里写图片描述
二 sin-demo.c
这里写图片描述
这里写图片描述
这里写图片描述
三 实现 kbhit()
我们先跑一遍输入函数
这里写图片描述
这里写图片描述
在Windows下实现基本功能:
这里写图片描述
这里写图片描述
这里写图片描述
代码:

#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#include<conio.h>
#include<windows.h>//linux使用unistd.h

#define SNAKE_MAX_LENGTH 20
#define SNAKE_HEAD 'H'
#define SNAKE_BODY 'X'
#define BLANK_CELL ' '
#define SNAKE_FOOD '$'
#define WALL_CELL '*'

//void snakeMove(int,int);
//void put_money(void);

int snakeX[SNAKE_MAX_LENGTH]={5,4,3,2,1};//蛇头是第一个,方便加身体长度
int snakeY[SNAKE_MAX_LENGTH]={1,1,1,1,1};
int snakeLength=5;
char map[12][13]=//卧槽,字符结尾还有\0
{
    "************",
    "*XXXXH  $  *",
    "*          *",
    "*          *",
    "*          *",
    "*          *",
    "*    $     *",
    "*          *",
    "*          *",
    "*          *",
    "*          *",
    "************"
};

void output()
{
    int i;
    for(i=0;i<12;i++)
    {
            printf("%s\n",map[i]);

    }
}

void gameover()
{
    printf("Game Over!!!");
}

char movable[4]={'W','A','S','D'};//可以走的方向
int distance[4]={0,0,0,0};//可走方向距离食物的距离
char whereGoNext()
{
    int i,j;
    int Hx,Hy;
    for(i=1;i<11;i++)
    {
        for(j=1;j<11;j++)
        {
            if(map[i][j]=='H')
            {
               Hx=i;
               Hy=j;
               break;
            }
        }
    }


    //判断A方向有没有食物,食物的距离
    int judge=0;
    for(j=Hx-1;j>0;j--)
        {
            if(map[j][Hy]=='$')
                judge++;
        }
    if(map[Hx-1][Hy]=='X')
        judge=0;//判断是否是身体
    if(judge>0)
    {
        for(j=Hx-1;map[j][Hy]!='$';j--)
        {
            if(map[j][Hy]==' ')
                distance[0]++;
        }
    }else{distance[0]=9999;}


    //判断W方向有没有食物,食物的距离
    judge=0;
    for(j=Hy-1;j>0;j--)
        {
            if(map[Hx][j]=='$')
                judge++;
        }
    if(map[Hx][Hy-1]=='X')
        judge=0;//判断是否是身体
    if(judge>0)
    {
        for(j=Hy-1;map[Hx][j]!='$';j--)
        {
            if(map[Hx][j]==' ')
                distance[1]++;
        }
    }else{distance[1]=9999;}


    //判断D方向有没有食物,食物的距离
    judge=0;
    for(j=Hx+1;j<11;j++)
        {
            if(map[j][Hy]=='$')
                judge++;
        }
    if(map[Hx+1][Hy]=='X')
        judge=0;//判断是否是身体
    if(judge>0)
    {
        for(j=Hx+1;map[j][Hy]!='$';j++)
        {
            if(map[j][Hy]==' ')
                distance[2]++;
        }
    }else{distance[2]=9999;}


    //判断S方向有没有食物,食物的距离
    judge=0;
    for(j=Hy+1;j<11;j++)
        {
            if(map[Hx][j]=='$')
                judge++;
        }
    if(map[Hx][Hy+1]=='X')
        judge=0;//判断是否是身体
    if(judge>0)
    {
        for(j=Hy+1;map[Hx][j]!='$';j++)
        {
            if(map[Hx][j]==' ')
                distance[3]++;
        }
    }else{distance[3]=9999;}

    //判断方向和输出
    int min=9999;
    for(i=0;i<4;i++)
    {
        min=(min<distance[i])?min:distance[i];
    }
    if(min==9999)
        return 'Q';
    for(i=0;i<4;i++)
    {
        if(min==distance[i])
            break;
    }
    return movable[i];
}
int main()
{
    int i;
    output();
    while(1)
    {
        Sleep(1000);//linux下sleep()
        char ch;

        ch=whereGoNext();
        //我们的游戏条件:必须是大写的asdw控制方向,否则退出!
        if(ch!='A'&&ch!='S'&&ch!='W'&&ch!='D')
            break;
        map[snakeY[snakeLength-1]][snakeX[snakeLength-1]]=' ';
        switch(ch)
        {
        case 'A':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeX[0]--;
            break;
        case 'D':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeX[0]++;
            break;
        case 'W':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeY[0]--;
            break;
        case 'S':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeY[0]++;
            break;
        }
        //判断有没有撞到障碍
        if(snakeX[0]<1||snakeX[0]>10||snakeY[0]<1||snakeY[0]>10)
            break;
        //吃食物长一节
        if(map[snakeY[0]][snakeX[0]]=='$')
        {
            snakeLength++;
            if(snakeX[snakeLength-2]==snakeX[snakeLength-3])
            {
                snakeX[snakeLength-1]=snakeX[snakeLength-2];
                snakeY[snakeLength-1]=2*snakeY[snakeLength-2]-snakeY[snakeLength-3];
            }else
            {
                snakeY[snakeLength-1]=snakeY[snakeLength-2];
                snakeX[snakeLength-1]=2*snakeX[snakeLength-2]-snakeX[snakeLength-3];

            }

        }
        for(i=1;i<snakeLength;i++)
        {
        map[snakeY[i]][snakeX[i]]='X';//先行后列
        }
        //判断有没有撞到身体
        if(map[snakeY[0]][snakeX[0]]=='X')
            break;

        //判断食物,如果遇到食物就长一节身体

        map[snakeY[0]][snakeX[0]]='H';

        output();

    }
    gameover();
    return 0;
}










额,上面是一个智障蛇,我会错题意了
改进:如果食物为0,退出
按照顺序寻找第一个食物,寻找最优路线

#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#include<conio.h>
#include<math.h>
#include<windows.h>//linux使用unistd.h

#define SNAKE_MAX_LENGTH 20
#define SNAKE_HEAD 'H'
#define SNAKE_BODY 'X'
#define BLANK_CELL ' '
#define SNAKE_FOOD '$'
#define WALL_CELL '*'

//void snakeMove(int,int);
//void put_money(void);

int snakeX[SNAKE_MAX_LENGTH]={5,4,3,2,1};//蛇头是第一个,方便加身体长度
int snakeY[SNAKE_MAX_LENGTH]={1,1,1,1,1};
int snakeLength=5;
char map[12][13]=//卧槽,字符结尾还有\0
{
    "************",
    "*XXXXH  $  *",
    "*          *",
    "*       $  *",
    "*          *",
    "*          *",
    "*    $     *",
    "*          *",
    "*          *",
    "*   $      *",
    "*          *",
    "************"
};

void output()
{
    int i;
    for(i=0;i<12;i++)
    {
            printf("%s\n",map[i]);

    }
}

void gameover()
{
    printf("Game Over!!!");
}

char movable[4]={'W','A','S','D'};//可以走的方向
int distance[4]={0,0,0,0};//可走方向距离食物的距离
char whereGoNext(int Hx,int Hy,int Fx,int Fy)
{

    //判断A方向距离
    if(map[Hx-1][Hy]=='X')
        distance[0]=9999;//判断是否是身体
    else
    {
        distance[0]=abs(Fx-Hx+1)+abs(Fy-Hy);
    }


    //判断W方向有没有食物,食物的距离
    if(map[Hx][Hy-1]=='X')
    {
        distance[1]=9999;
    }else
    {
        distance[1]=abs(Fx-Hx)+abs(Fy-Hy+1);
    }

    //判断D方向有没有食物,食物的距离
    if(map[Hx+1][Hy]=='X')
    {
        distance[2]=9999;
    }else
    {
        distance[2]=abs(Fx-Hx-1)+abs(Fy-Hy);
    }


    //判断S方向有没有食物,食物的距离
    if(map[Hx][Hy+1]=='X')
    {
        distance[3]=9999;
    }else
    {
        distance[3]=abs(Fx-Hx)+abs(Fy-Hy-1);
    }

    //判断方向和输出
    int min=9999;
    int i;
    for(i=0;i<4;i++)
    {
        min=(min<distance[i])?min:distance[i];
    }
    if(min==9999)
        return 'Q';
    for(i=0;i<4;i++)
    {
        if(min==distance[i])
            break;
    }
    return movable[i];
}
int main()
{
    output();
    while(1)
    {
    int i,j;
    int Hx,Hy,Fx,Fy;
    for(i=1;i<11;i++)
    {
        for(j=1;j<11;j++)
        {
            if(map[i][j]=='H')
            {
               Hx=i;
               Hy=j;
               break;
            }
        }
    }

    //顺序查找,找到第一个食物
    int flag=0;
    for(i=1;i<11;i++)
    {
        if(flag==1)
            break;
        for(j=1;j<11;j++)
        {
            if(flag==1)
                break;
            if(map[i][j]=='$')
            {
               Fx=i;
               Fy=j;
               flag=1;
            }
        }
    }

       Sleep(1000);//linux下sleep()
        char ch;

        ch=whereGoNext(Hx,Hy,Fx,Fy);
        //我们的游戏条件:必须是大写的asdw控制方向,否则退出!

        //如果没有食物就退出,否则陷入死循环
        int flag1=0;
        for(i=1;i<11;i++)
        {
        for(j=1;j<11;j++)
        {
            if(map[i][j]=='$')
            {
               flag1++;
            }
        }
        }
        if(flag1==0)
        {ch='Q';}
        if(ch!='A'&&ch!='S'&&ch!='W'&&ch!='D')
            break;
        map[snakeY[snakeLength-1]][snakeX[snakeLength-1]]=' ';
        switch(ch)
        {
        case 'A':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeX[0]--;
            break;
        case 'D':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeX[0]++;
            break;
        case 'W':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeY[0]--;
            break;
        case 'S':
            for(i=snakeLength-1;i>0;i--)
            {
                snakeX[i]=snakeX[i-1];
                snakeY[i]=snakeY[i-1];
            }
            snakeY[0]++;
            break;
        }
        //判断有没有撞到障碍
        if(snakeX[0]<1||snakeX[0]>10||snakeY[0]<1||snakeY[0]>10)
            break;
        //吃食物长一节
        if(map[snakeY[0]][snakeX[0]]=='$')
        {
            snakeLength++;
            if(snakeX[snakeLength-2]==snakeX[snakeLength-3])
            {
                snakeX[snakeLength-1]=snakeX[snakeLength-2];
                snakeY[snakeLength-1]=2*snakeY[snakeLength-2]-snakeY[snakeLength-3];
            }else
            {
                snakeY[snakeLength-1]=snakeY[snakeLength-2];
                snakeX[snakeLength-1]=2*snakeX[snakeLength-2]-snakeX[snakeLength-3];

            }

        }
        for(i=1;i<snakeLength;i++)
        {
        map[snakeY[i]][snakeX[i]]='X';//先行后列
        }
        //判断有没有撞到身体
        if(map[snakeY[0]][snakeX[0]]=='X')
            break;

        //判断食物,如果遇到食物就长一节身体

        map[snakeY[0]][snakeX[0]]='H';

        output();

    }
    gameover();
    return 0;
}










效果图:
这里写图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值