控制台RPG开发教程7: 筹建地图工作组5(地图的数据表现)

本次教程的内容:

  1. 数组的概念
  2. for循环
  3. 字符串的概念

上一次课程最后的代码,已经实现了用键盘控制英雄移动。但还有两个地方明显不正常。
首先是画面上的墙,形同虚设,不但能穿墙而过,并且走过之处把墙也消除掉了。
你可以走出了上边或左边的屏幕,并导致画面出现混乱。
我们应当在程序中对此种情况加以控制。

具体的控制方法是这样的,我们在移动英雄之前,先做一个判断:
如果前面是空地,就可以让英雄走过去,如果是墙,就不能移动。
如果前面走出了地图的边界,也不能移动。

我们已经有了英雄的位置坐标(x, y),我们只需再知道地图的数据就可以做出这种判断。
现在的地图信息,是通过一个常量字符串直接写到语句输出到屏幕了。
一旦这句输出指令运行完毕,我们再想找到这些信息就困难了。
我们这里引入数组的概念,来保存地图信息。
所谓数组,就是精灵大楼中一串相邻的房间,它们被贴了一个统一的标签,同时每个房间又有自己独立的编号。
第一个房间是0号,第二个是1号,依此类推,第N个就是N-1号。编号放在方括号内表示。
我们的地图有五行,每行由一个字符串表示。
我们先把最早的map1.cpp做一个修改,换一个方式来显示地图。

# include <iostream>
# include <conio.h>
# include <windows.h> 
using namespace std;

int main(){
    string mapInfo[5];
    mapInfo[0]= "■■■■■■■■■■■■";
    mapInfo[1]= "♀      ■■          ■";
    mapInfo[2]= "■  ■    ■■  ■■  ■";
    mapInfo[3]= "■  ■■        ■      ";
    mapInfo[4]= "■■■■■■■■■■■■";
    for (int i=0; i< 5; i++){
        cout << mapInfo[i]<< endl;
    }
}

main函数中的第一行是定义数组的语句。我们规定了,大楼中有5个房间连起来,统称mapInfo(地图信息)。
这5个房间,具体分别叫做mapInfo[0] ~ mapInfo[4]
我们通过后面的4条赋值语句,将每一行地图的具体数据保存到了房间中。
每个房间存储的都是一个文本信息,也叫做字符串。或者说,每个房间的格局都是string类型。我们前面学过int类型的房间,一般固定占有4个字节的大小,string类型的房间格局又有所不同,我们一会详细介绍它。

接下来是一条新语句,它其实是另外一种形式的循环语句。
与前面使用过的无限循环不同,这里我们只需循环5次即可。这种有着固定循环次数的情景,使用for语句比较清晰。
for语句结构比较复杂,我们仔细分析一下这条语句。
for 后面是一个括号,括号内由分号分成了三个部分,其实就是三条指令。
其中第一条指令,将在进入for语句后首先执行,只执行一次。我们看到,它定义了一个变量名叫i,并且给它一个初始值0。
第二条指令,将会被随后执行,i < 5,这是一个由“<”符号标志的电话功能指令,精灵会让数学工作组判断i的值是否小于5。
这类功能指令,与+ - * / 类似,我们也常把+ - * / 等运算符所标志的功能指令称作算术表达式
而把 > < >= <= == != 等六个符号标志的功能指令称作关系表达式
前面4个含义都很明确,和我们在数学课上的使用符号是一样的,值得特别注意的是后两个:
== 两个等号,代表关系表达式的相等判断,!= 代表关系表达式的不相等判断。
对比一下:= 一个等于,则是给变量赋值使用的赋值表达式。精灵执行这条语句,一般自己亲自操作。
此外,还有一种逻辑表达式,我们很快会遇到。
至于我们在输出和输入中曾见到的 << >> 也是一种表达式,但很少有人给它们专门起名字。
如果条件满足,将会开始执行后面的大括号内的第一条指令。否则,将跳过大括号,执行大括号后面的第一条指令。
在开始,i=0,当然 i < 5,所以进入大括号执行将mapInfo[i],也就是mapInfo[0]的内容输出到屏幕的光标所在位置。
大括号内的指令全部执行完毕后,将会执行

第三指令。i++
这是一个简写的指令,它的含义是i=i+1,其中包含两个动作。把变量i中的数字+1后,再放回变量i中。
这种将+1后放回原变量的操做写成++的形式,是c语言的一个鲜明特色。
所以当一种扩展了的c语言出现后,人们就把它命名为c++。
再往后,微软推出了另外一种与c和c++语言都相类似,但据说更先进的语言。
微软把它命名为c#,从形象上来看,#好像是两个+的重叠,致敬了c++。
同时又是音乐符号中升半音的意思,代表了提升。

第三条指令后,精灵回再次回到第二条指令,做判断,然后继续。
画一个图形表示,是这样的。

我们已经把地图数据保存在mapInfo数组变量中了,下一步,让我们看看怎样找到地图上一个位置的内容,究竟是墙还是道路。

让我们深入研究一下存储字符串数据的房间格局。
如果一个房间里保存的是字符串,我们走进之后会发现,实际上它的里面是由很多小房间组成的。
每个房间的大小是一个字节。其中第一个房间命名为0号,存放的是第一个字符;第二个命名为1号,存放的是第二个字符;直到我们走到某个房间,发现里面存放的是0,我们就知道已经走到头了。
所以说,字符串其实也是一个数组,它是字符组成的数组。
那么精灵怎么访问字符串中的内容呢?同样是通过中括号。
比如如果想看看地图上,英雄初始位置的右边是什么,我们就应该使用mapInfo[1][2]
其中,第一个中括号中的1代表地图的行,也是英雄的y坐标。
英雄的初始位置是0,由于是中文字符,向右一步则是+2,所以第二个中括号中的2代表英雄右边一个的内容。
一般情况下,我们用if 语句来判断英雄是否可以向右走,我们这样写

if (mapInfo[y][x+ 2]== ' ') {
    // 向右移动的代码
}


注意,这里出现了单引号,在c++中单个字符用单引号表示,字符串用双引号来表示。
这里,字符串房间中的一个小房间里存储的是一个字符,所以就应当用单引号来表示了。这里把完整的代码贴上来

# include <iostream>
# include <conio.h>
# include <windows.h>
using namespace std;

void gotoxy(unsigned char x,unsigned char y){
    COORD cor;
    HANDLE hout;
    cor.X = x;
    cor.Y = y;
    hout = GetStdHandle(STD_OUTPUT_HANDLE);
    SetConsoleCursorPosition(hout, cor);
}

int main(){
    string mapInfo[5];
    mapInfo[0]= "■■■■■■■■■■■■";
    mapInfo[1]= "♀      ■■          ■";
    mapInfo[2]= "■  ■    ■■  ■■  ■";
    mapInfo[3]= "■  ■■        ■      ";
    mapInfo[4]= "■■■■■■■■■■■■";
    for (int i=0; i< 5; i++){
        cout << mapInfo[i]<< endl;
    }
    int x, y;
    x= 0;
    y= 1;
    int a;
    while(1){
        a= getch();
        if (a==72) {
           // 向上 
           if (mapInfo[y- 1][x]== ' ') {
               gotoxy(x,y);
               cout << "  ";
               y= y- 1;
               gotoxy(x,y);
               cout << "♀";
           }
        }
        if (a==80) {
           // 向下 
           if (mapInfo[y+ 1][x]== ' ') {
               gotoxy(x,y);
               cout << "  ";
               y= y+ 1;
               gotoxy(x,y);
               cout << "♀";
           }
        }
        if (a==75) {
           // 向左 
           if (mapInfo[y][x- 2]== ' ') {
               gotoxy(x,y);
               cout << "  ";
               x= x- 2;
               gotoxy(x,y);
               cout << "♀";
           } 
        }
        if (a==77) {
           // 向右 
           if (mapInfo[y][x+ 2]== ' ') {
               gotoxy(x,y);
               cout << "  ";
               x= x+ 2;
               gotoxy(x,y);
               cout << "♀";
           } 
        }
    }
}

课程小结:


c++编程中的两种引号,我们都已经遇到了。
两种引号:

  • 单引号:表示单个字符
  • 双引号:表示字符串

另外,数组的概念,for语句的理解,字符串的基本操作,是本课的重点。
请大家运行最后的代码,看看是否还有哪些怪异不合理的地方。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

圣手书生肖让

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值