找回密码
 马上注册

QQ登录

只需一步,快速开始

楼主: James.Yang

[教程] LEGO MINDSTORMS NXT编程指南(完整中文版)——自主翻译

   火.. [复制链接]
 楼主| 发表于 2012-12-19 19:37:06 | 显示全部楼层
本帖最后由 James.Yang 于 2012-12-19 19:38 编辑

第16章 内部还是外部?
在上一章中,你已经学习了如何使用比较模块来测试一个值是小于、大于还是等于另一个值。比较模块比较两个数字并判断语句(A小于B,A大于B,或者A等于B)是真是假。
然而,有时你要检测某个值是否在一定的数值范围内还是在范围外:28在2到30之间吗?正确。50在1到60之外吗?错误。
NXT-G提供了一个模块,允许你检测一个数字(A)是落在另外两个数(B和C)之间还是之外。以下介绍它是如何工作的。
范围模块
如同比较模块一样,范围模块也采用以下的规则:机器人对语句的判断响应为真或假。
范围模块将评估的语句就同下述语句相似:
        数A在数B开始和数C结束的数值范围之内。
        数A在数B开始和数C结束的数值范围之外。
就这么两种方式。范围模块评估语句并返回一个真或假的反馈。我们为SPOT创建一个可能使用范围模块的小程序。照例,我们还是从伪代码开始:
[我]:SPOT,请产生一个1到100之间的随机数,显示在LCD屏幕上,并且告诉我这个值是否在40与60之间。
为了完成这个任务,我们在顺序条上放置一个随机模块,其配置如图16-1所示。

图16-1  随机模块产生20到80之间的随机数

下一步,我使用数字转文本模块将其转换为文本(见图16-2)。因为我要将这个随机数字显示在LCD屏幕上,所以必面要用到数字转文本模块。

图16-2  将随机数转换为文本

下一步,我将添加一个文本模块来创建一个语句“A在40和60范围内。”如图16-3所示。

图16-3  创建一个显示在LCD屏幕上的文本语句

在图16-3中,随机模块产生的数字作为数字转文本模块的输入,然后文本模块将此文本作为文本A的输入,并与语句“在范围内”进行组合。
在图16-4中,我使用数据线将文本模块发送数据给显示模块,并将显示模块配置显示在第3行X=2,Y=40的位置(见图16-4)。

图16-4  显示模块将显示“[数字]在范围内。”

我还需要添加一个显示模块,这样我能在第4行X=2,Y=32的位置添加文本“40和60”(见图16-5)。请记住,不要选中清除复选框,这样第一个显示模块的文本不会消失。

图16-5  这个显示模块将“40和60”显示在屏幕的下一行
现在是时间使用范围模块来评估语句了。我拖放了范围模块到顺序条,如图16-6所示。

图16-6  范围模块将检查数A是否在40和60范围之内

在图16-6中,你可以看到我在操作部分的下拉菜单中选择了范围之内。我同时在字段A内输入了40,字段B内输入了60。我还可以使用滑动条来选择范围的下限值和上限值,但要注意滑动条只允许你选择0到100之间的范围。如果你需要一个更大的范围,你必须人工输入数值。
同时,我不需要在测试值字段内输入数值,因为我使用了数据线将随机数输入到范围模块。


注意:在操作部分下拉菜单的另一个选项是范围之外。如果我选择这个选项,当随机数在40和60范围之外时,语句为真,当随机数在范围之内时,语句为假。另外需要注意的是测试值可以直接在测试字段内输入。如果没有从外部模块(如随机模块)得到数值作为输入,你可以使用该字段。最后,上限值与下限值同样也可以通过数据线提供输入(数字类型)给上限数据接头和下限数据接头来动态提供给范围模块。


下一步是将原始的随机数字通过数据线输入给范围模块。有两种方法可以完成这一点,第一种方法是从数字转文本模块(记得该模块具有原样输出数字的数据接头)的输出接头拉数据线,我在第15章对比较模块使用过这种方法。现在我将向你展示另外一种方法。
如果你点击随机模块输出数字数据接头,你可以连根数据线到范围模块的输入测试值数据接头。图16-7已按此方法完成了数据线。请注意原来输入到数字转文本模块的数据线已被分割成两根数据线——一根还是连到数字转文本模块,另一根连到了范围模块。

图16-7  测试值用来评估它是否在范围40和60之内

伪代码告诉SPOT在LCD屏幕上显示语句“[数值]在范围40和60之间”是真还是假。要完成这一点,我在范围模块后面拖放了一个开关模块。在显示部分,我没有选择平面视图复选框;在控制部分,我选择了值,在类型部分,我选择了逻辑。我同时从范围模块的输出结果数据接头连接了数据线到开关模块的输入数据接头(见图16-8)。

图16-8  开关模块将帮助我在屏幕上显示真或假

现在只剩下在LCD屏幕上显示真或假。这个很简单:我在真选项卡上拖放了一个显示模块(见图16-9),将文字真显示在LCD屏幕第7行。在假选项卡上放置了另一个显示模块(见图16-10),将文字假显示在LCD屏幕上第7行(记住不要选中清除复选框以免LCD屏幕上的文字被擦除)。我将“真”或“假”文字定位在LCD屏幕X=12,Y=8的位置。

图16-9  显示模块将“真”显示在屏幕上


图16-10  显示模块将“假”显示在屏幕上

现在,如果语句是真的,开关模块将执行真选项卡上的显示模块;如果语句是假的,开关模块将执行假选项卡上的显示模块。
下一步,我拖放了一个NXT按钮等待模块,并配置为当左键按下后,中止等待(见图16-11),这将使我有时间来看到结果。

图16-11  NXT按钮等待模块让你有时间看清结果

现在我给你一个练习,如果你对刚才创建的程序理解的话,这不是很难。在本章的结尾,我结出了一个可能的解决方案。
练习16-1 范围之外
修改程序,使用两个随机模块给范围模块创建上限值与下限值。下限值在30到40之间,上限值应该在50到60之间。使用第三个随机模块来产生一个在5到95之间的随机数作为测试值,并测试该值是否在范围之外。使用显示模块来显示上限值,下限值及测试值,并根据测试值是否落在范围外显示“真”或“假”。
下一步内容?
你结束本章后,将继续学习第17章的逻辑模块。你应该对逻辑及如何评价真假语句有很好的理解了;逻辑模块将使你在得到真或假的回答前,允许你控制如何评估项目,以给你的机器人更强大的能力。
练习解决方案
图16-12到图16-23给出了练习16-1的完整程序和配置面板。记住不要勾选显示模块的清除复选框,这样文本不会被清除。

图16-12  完整的程序和下限值随机模块的配置面板


图16-13  上限值随机模块的配置面板


图16-14  第一个数字转文本模块的配置面板


图16-15  第二个数字转文本模块的配置面板


图16-16  文本模块的配置面板

图16-17  第一个显示模块的配置面板


图16-18  第二个显示模块的配置面板


图16-19  范围模块的配置面板


图16-20  开关模块的配置面板


图16-21  真路径上显示模块的配置面板


图16-22  假路径上显示模块的配置面板


图16-23  NXT按钮等待模块的配置面板
图16-1.JPG
图16-2.JPG
图16-3.JPG
图16-4.JPG
图16-5.JPG
图16-6.JPG
图16-7.JPG
图16-8.JPG
图16-9.JPG
图16-10.JPG
图16-11.JPG
图16-12.JPG
图16-13.JPG
图16-14.JPG
图16-15.JPG
图16-16.JPG
图16-17.JPG
图16-18.JPG
图16-19.JPG
图16-20.JPG
图16-21.JPG
图16-22.JPG
图16-23.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2012-12-23 19:22:24 | 显示全部楼层
本帖最后由 James.Yang 于 2012-12-23 19:23 编辑

第17章 是?否?可能?
在第15章,我向你介绍了比较模块,它可以对两个数字A和B进行检查以确定A是否大于,小于还是等于B(依赖于你所选择的选项),这个比较的结果将转换为一个逻辑数据类型(真或假)并能通过数据线输出。在第16章,我向你展示了怎样使用范围模块来检查一个值是否落在上限值与下限值之间——同样将得到一个真或假的回答。
本章,我将向你展示一个与比较模块和范围模块类似,但不是完全相同的模块。这个模块将比较两个逻辑数据类型的输入而不是比较两个数值,同样得到一个真/假的逻辑数据类型的输出。
逻辑模块
逻辑模块是一个非常有趣的模块(如图17-1所示)。

图17-1  逻辑模块和它的配置面板

让我给SPOT建立一个游戏以有助于你了解逻辑模块是如何工作的。我给SPOT安装了一个光线传感器和声音传感器,以下是我给SPOT试验的第一个伪代码。
        [我]:SPOT,如果两个条件都为真时向前移动3圈。
        [我]:第一个条件是光线传感器检测到的光线值低于30.
        [我]:第二个条件是声音传感器检测到的声音值低于20.
现在会发生什么呢?是这样的,SPOT将检查其光线传感器检测到房间内的光线值是否较低(<30)。他同时要检查其声音传感器是否检测到一个安静的房间(<20)。回想一下对传感器的讨论,传感器能根据你配置传感器要检测的条件而返回一个真或假的响应。
我们从拖放一个光线传感器到顺序条并配置它来开始这个程序,如图17-2所示的配置面板。

图17-2  以如图所示的配置面板来配置光线传感器

下一步,你将添加一个声音模块,其配置如图17-3所示。

图17-3  以如图所示的配置面板来配置声音传感器

现在你有两个传感器来检查房间内的光线和声音。
如果回头看一下伪代码,SPOT只有在两个传感器都被触发的情况下才向前移动。这意味着光线传感器必须接受到房间内的光线值小于30,且声音传感器必须接受到房间内的声音值小于20——两个条件必须同时满足,否则SPOT不会向前移动。
&#61599;        如果房间明亮且安静将会发生什么?SPOT不会移动。
&#61599;        如果房间黑暗且吵闹将会发生什么?SPOT仍然不会移动。
&#61599;        如果房间明亮且吵闹将会发生什么?SPOT将头大了,开个小玩笑——SPOT仍然不移动。
正如你能想到的,他只有在房间安静且黑暗时才会移动。
因此,SPOT如何才能快速检测房间内的光线和声音条件,以决定他是否能向前移动?简单——他将使用比较模块。
接下来,拖放一个逻辑模块到顺序条,如图17-4所示。

图17-4  逻辑模块帮助SPOT来检测光线和声音条件

看一下操作部分的下拉菜单。下拉菜单有四个选项:与,或,异或及非。现在选择与选项,(我随后会对其它三个选项进行解释)。
下一步,我希望你从光线传感器模块的是/否数据接头连根数据线到逻辑模块的A输入数据接头,如图17-5所示。

图17-5  连接光线传感器模块到逻辑模块

从声音传感器模块的是/否数据接头连根数据线到逻辑模块的B输入数据接头,如图17-6所示。

图17-6  连接声音传感器模块到逻辑模块

现在让我来解释到目前为止会发生什么。逻辑模块从光线传感器接收一个是/否响应,同时也从声音传感器接收一个是/否响应。通过在逻辑模块选择与选项,你强制逻辑模块从接头A(是或否)及接头B(是或否)得到结果,将它们在一起作加运算以得到单一的是/否响应。我已经听到你在问,“你怎么将是/否响应进行加运算?”
不错,答案很简单,且依赖于你在下拉菜单中的选项(与,或,异或,及非选项):

与选项:如果你选择与选项,要得到一个最终的是结果,两个响应必须都为是。如果接头A为是且接头B为否,最终结果将为否。同样,如果接头A为否且接头B为是,最终结果仍为否。如果接头A为否且接头B为否,最终结果为否。只有当两个输入都为是时,才能产生一个是结果。

或选项:如果你选择或选项,要得到一个最终的是结果,只要一个响应为是就可以了。如果接头A为是且接头B为否,最终结果将为是。同样,如果接头A为否且接头B为是,最终结果仍为是。如果接头A与接头B都为是,最终结果也会是。只有当接头A和接头B都为否时,最终结果才为否。

异或选项:这是一个奇怪的符号。如果你选择异或选项,只有一个接头为是时,最终结果为是。如果接头A为是且接头B为否,最终结果为是。同样,如果接头A为否且接头B为是,最终结果仍然为是。然而,如果接头A和接头B都为是最终结果为否。如果接头A和接头B都为否,最终结果为否。记住,要得到是输出响应,只有一个逻辑输入值为是……只能有一个。

非选项:这又是一个奇怪的符号。这个选项实际上不是返回一个最终结果——它只是改变接头A的逻辑值输入作为它的响应。例如:如果接头A为是,那么接头A的输出为否。这个选项只是对逻辑值取反而没有其它结果。要注意接头B在非选项中是不起作用的。

现在,让我们完成你的例子程序。如果你回头看一下图17-6,你现在已拥有逻辑模块来提供是/否响应(使用数据线)。
你是否还记得,你是在测试声音传感器检测到声音的是否低于30和光线传感器检测到的值是否小于20。如果这两个条件都为真,则SPOT将允许向前移动3圈。如果两个条件有一个不真,SPOT将不会移动。
因此,你下一步要拖放一个开关模块来测试逻辑模块的条件。首先,从控制部分的下拉菜单中选择值。然后,从类型部分的下拉菜单中选择逻辑。选中平面视图复选框,因为你只有两个可能的选项(真或假)。这个配置见图17-7。

图17-7  开关模块将使用逻辑模块的输出来控制SPOT的行动。

现在,你能使SPOT有一点智能了。如果光线传感器检测到的光线值低于30,它将向逻辑模块发送一个真值。如果声音传感器检测到的声音值低于20,它将向逻辑模块发送一个真值。你已配置逻辑模块使用与选项,因为你想检测两个条件都为真。如果它们都为真,逻辑模块将发送一个真(是)信号给开关模块。如果两个条件中有一个为假,逻辑模块将发送一个假信号给开关模块。
现在剩下的就是在开关模块的真路径上放置一个移动模块,如图17-8所示。

图17-8  移动模块被配置为向前移动3圈

如果开关模块检测到逻辑模块一个真响应,移动模块执行(向前移动3圈),程序结束。如果开关模块检测到逻辑模块一个假响应,没有额外的模块要执行,SPOT没有移动,程序结束。现在还需要的是在程序的结尾添加一个NXT按钮等待模块,以等待移动模块完成动作并等待用户按下按钮来终止程序。
我想你应该已掌握了逻辑模块?然后我们来看一下练习17-1。如果你有困难,我在本章结尾放置了练习的一个可能的解决方案。
练习17-1:SPOT寻找场景
在一条直线上放置一系列的蓝色和红色的圆圈。让SPOT按照圆周向前移动。当SPOT超过红圆圈时,大喊“停止!”建立一个程序,当检测到红色且声音传感器检测到声音值超过75时,停止SPOT的运动。
下一步内容?
逻辑模块对两个逻辑数据类型响应(是/否或者真/假),将它们进行“加运算”得到一个逻辑数据类型是非常有用的工具。你是否在想如果有四个逻辑数据输入且需要将他们组合在一起,你该怎么做?你需要使用两个逻辑模块:每个模块将采用两个逻辑数据输入值并提供一个最终的逻辑响应。你可以在图17-9看到。这两个逻辑响应将使用第三个逻辑模块进行组合以得一个真正的“最终”逻辑响应。是否有点混乱?有一点,但当你开始使用逻辑模块后,你将开始看到它将与循环模块及开关模块一起使用将会给机器人更好的决策能力。

图17-9  多个逻辑模块输入到一个逻辑模块
练习解决方案
图17-10到图17-14显示了练习17-1的完整程序及配置面板。移动模块将无限运转电机,直到循环中止,程序结束。

图17-10  完整的程序及移动模块的配置面板


图17-11  循环模块的配置面板

图17-12  颜色传感器的配置面板


图17-13  声音传感器的配置面板


图17-14  逻辑模块的配置面板
图17-1.JPG
图17-2.JPG
图17-3.JPG
图17-4.JPG
图17-5.JPG
图17-6.JPG
图17-7.JPG
图17-8.JPG
图17-9.JPG
图17-10.JPG
图17-11.JPG
图17-12.JPG
图17-13.JPG
图17-14.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2012-12-24 15:07:24 | 显示全部楼层
顶起,楼主 谢谢!
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2012-12-26 21:15:45 | 显示全部楼层
James.Yang 发表于 2012-12-23 19:22
第17章 是?否?可能?
在第15章,我向你介绍了比较模块,它可以对两个数字A和B进行检查以确定A是否大于, ...

谢谢楼主,顶你!后续期待中。。。。
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2012-12-27 16:32:37 | 显示全部楼层
楼主大好人一枚!
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2012-12-28 21:08:17 | 显示全部楼层
本帖最后由 James.Yang 于 2012-12-28 21:09 编辑

第18章 标题=任何你喜欢的
这是个奇怪的标题,不是吗?你可以选择任何你喜欢的作为标题。但并不意味着本章介绍的内容会发生改变。不会改变,本章将包含两个特殊的模块称为变量模块和常量模块。你会发现,当需要存贮一些信息以便后面使用时,这两个模块是很有用的。这一章有点冗长,因此本章没有任何练习。但本章的信息让你的机器人具有贮存信息以便给今后使用的能力是非常有价值的,因此,慢慢阅读并确实理解这两个新模块是怎样使用的和什么时候使用。让我们往下看。
变量模块
让我们想象一会你想让SPOT记住一些信息,这些信息包含有一些文字,一些数字及几个逻辑真/假值。SPOT具有将每个信息放入他存贮器内虚拟文件夹的能力。然而,这些信息将随着程序的结束或者智能积木块的关闭而消失。下面是伪代码:
[我]:SPOT,你能存贮文字“pizza”和“cheesecake”在你的存贮器里吗?
[我]:SPOT,同时要求你贮存数字“50”和“200”在你的存贮器里。
[我]:SPOT,你能存贮一个逻辑“真”和一个逻辑“假”在你的存贮器里吗?
现在,在将这个伪代码转换为NXT-G程序之前,我必须告诉你一些关于NXT-G程序如何存贮信息,改变信息及找回信息的。所有这些可以使用变量模块和常量模块来实现。我先介绍变量模块,因为一旦你理解了变量模块是如何工作的,你将会理解常量模块是如何工作的,因为常量模块几乎是用相同的方式工作的(但有一个明显的例外,我会在后面揭露它)。
一个变量模块能完成以下两件事之一:
&#61599;        信息能被写入存贮在存贮器里的虚拟文件夹内。
&#61599;        信息能从存贮在存贮器里虚拟文件夹内读取。
这些虚拟文件夹也称为变量。一个NXT-G变量只能配置用于存贮三种数据类型之一:文本,数字及逻辑(真或假)。
文本非常简单;我的伪代码要求SPOT存贮“pizza”和“cheesecake”,但这如同告诉SPOT存贮字母“A”或者句子“My name is SPOT.”一样简单。
数字更简单:当一个NXT-G 2.0的变量模块被配置为存贮一个数字时,它仅能存贮正数及负数,例子包括5,-3.0和101.25。然而,对NXT-G 1.0版本软件用户,变量模块被限制在正整数及负整数,因此数值如4.5或-10.2将被取整到最近的整数(例子中被取整为5及-10)。
逻辑数据只有两个选择:真或假。NXT-G变量模块被配置为存贮逻辑值时只能存贮真或假,而不能是其它。
探索变量模块
好了,现在是时间来看一下变量模块了。这个模块可以在完整面板数据弹出菜单中找到。选择变量模块,拖放到顺序条(见图18-1)。

图18-1  变量模块和它的配置面板

我提醒过你,信息能从变量模块读取或写入。在图18-1中,你将注意到,在默认情况,当你第一次拖放一个变量模块到顺序条时,它被配置为读取(在动作部分)一个逻辑类型值,这个变量同时被被命名为:Logic 1。
这意味着如果真或假存贮在变量中,这个数值能够从变量中读取。注意到数值部分是灰色的,它表明你不能编辑它。同时注意到在数值部分默认选择的数值为假。
在我展示如何修改它之前,在变量模块配置面板选择变量名字为Number 1(见图18-2)。

图18-2  选择Number 1作为变量名的变量模块

如果你选择Number 1作为变量名,你将看到存贮的默认值为0。这个数字是从变量Number 1读取的值。
下一步,在变量模块配置面板选择Text 1(见图18-3)。

图18-3  选择Text 1作为变量名的变量模块

如果你选择Text 1作为变量名,默认值为空白,在Text 1变量中没有存贮文本。
读取变量
在图18-1,18-2,18-3中,同时也注意到每个模块都只有一个输出数据接头,这与我们知道的在变量模块配置面板中动作部分被配置为读取是相匹配的。变量只能被读取;其它模块(如显示模块)将通过数据线使用这个输出数据接头作为输入。这称为从变量读取。
为了确保你能理解这个概念,请看图18-4,我将作进一步解释。

图18-4  一个变量模块提供它的变量值给另外一个模块
在图18-4中,我将一个称为Logic 1的变量模块连接到一个开关模块。开关模块的配置面板可以在图18-4中看到,你可以看到我将开关模块类型部分配置为检查逻辑值。当程序执行时,开关模块将从变量模块读取数值。如果数值为真,开关模块将执行我放置在真路径上的声音模块。如果数值为假,开关模块将执行我放置在假路径的移动模块。
写入变量
现在,那个例子涉及将直接从变量模块读取数据。如果我要放入些数据该怎么办?那么我必须写入数据到模块。下面将介绍怎样来完成它。
看一下图18-5,在这个图中,我在动作部分选择了写入。

图18-5  在动作部分选择写入的变量模块

在图18-5,我能够改变逻辑值。还记得其默认值为假,因此我改变它为真。你是否还注意到在数据中心添加了一个输入数据接头?这意味着我可以通过数据线从其它模块来决定它的真或假值。(在这个例子中,数据线必须传递一个真或假的逻辑值,另外其它类型的值将会使数据线为虚线,且不能运行。同样,如果在列表部分选择数值或文本,输入数据线必须提供所选项目的数据类型。)
图18-6显示了Number 1和Text 1模块的配置面板。我包含他们,是因为我想让你知道当将动作部分设置为写入后怎样来修改数据。对变量Number 1,你可以在数值字段输入正数或负数。对变量Text 1,你可以在数值字段输入词,句子甚至整个一段文字。

图18-6  变量Number 1和Text 1选择了写入的变量模块

在将变量模块内的数据修改后,你可以通过在动作菜单内选择读取来关闭模块(这就防止数据被修改)或者就直接不管这个模块。如果你保留动作部分为写入,你可能从其它模块连接数据线到变量模块的输入数据接头(要记住进入输入数据接头的数据类型要与变量被配置的数据类型(文本,数字及逻辑)相匹配)。
存贮很多值
现在让我们回到我给SPOT的原始伪代码:
[我]:SPOT,你能存贮文字“pizza”和“cheesecake”在你的存贮器里吗?
[我]:SPOT,同时要求你存贮数字“50”和“200”在你的存贮器里。
[我]:SPOT,你能存贮一个逻辑“真”及一个逻辑“假”在你的存贮器里吗?
你发现其中的问题吗?我要求存贮两个文本及两个数字。我已经知道变量模块只能拥有一个数据。例如,如果我存贮数字50到变量Number 1中,数字200将存贮在什么地方?同样我可以存贮“pizza”到变量Text 1中,那么“cheesecake”存贮在什么地方?
答案很简单。NXT-G允许你按要求创建多个变量。你甚至可以将一个变量重命名,就象Text 1可以重命名为容易记住的“Food”,或者Number 1重命名为“Test Scores”。下面有介绍重命名的方法。
如果你需要创建另一个变量,点击NXT-G软件上方的编辑菜单,点击定义变量菜单选项。
一个如图18-7的小窗口将被打开。

图18-7  编辑变量窗口允许你创建新变量

点击创建按钮,一个具有如MyVariable_1默认名字的新变量将出现在列表部分,(见图18-8)。

图18-8  你的新变量将出现在列表部分

你可以在名字字段内输入一个新名字来改变变量的名字。在数据类型部分的下拉菜单中选择存贮变量的数据类型。我已经将我的新变量命名为Test Scores且配置为存贮数字(见图18-9)。你可以再次按下创建按钮来创建另一个变量,结束后按关闭按钮。

图18-9  给新变量一个名字及拥有的数据类型

现在,当你将变量模块拖放到顺序条时,你会注意到你的新变量作为一个选项将出现在列表部分(见图18-10)。使用这个方法,你可以按你要求创建多个文本、数字及逻辑变量。

图18-10  你新创建的变量显示在配置面板的列表部分
解决例子中的问题
好的,现在你知道如何放置数据到变量(写入)及如何从变量取得数据(读取),你同时也知道怎样创建额外的变量,你现在需要学习的是在整个程序中如何使用变量。
下面是给SPOT的一些伪代码:
[我]:SPOT,从1数到3,然后检查左键是否按下,如果左键被按下,发送一个真逻辑值给变量名为Pressed的变量模块;如果左键没有被按下,发送一个假逻辑值给变量模块。
[我]:然后,从3倒数到1,结束数数后,根据变量模块中读取到的真/假逻辑值,在LCD屏幕上相应显示“按下”或者“未按下”。
[我]:当右键按下后,停止程序。
首先我拖放了3个声音模块并配置为从1数到3。所有三个声音模块及最后一个模块的配置面板如图18-11所示。

图18-11  开始的三个声音模块将从1数到3

然后,我拖放一个NXT按钮传感器模块并配置它检测左键按下(见图18-12)。

图18-12  NXT按钮传感器模块将检测左键按下

我创建了一个命名为“Pressed”的逻辑类型变量模块。然后在NXT按钮传感器模块后面拖放一个变量模块,并在动作部分选择我新建的变量Pressed,并选择为写入。我从NXT按钮传感器模块的输出数据接头连接数据线到变量模块的输入数据接头(见图18-13)。

图18-13  变量Pressed将拥有真或假值

如果从1数3结束时,立即按下左键,NXT按钮传感器将检测按下,并改变逻辑值为真。当程序开始时,原始的值为假,但是当数数结束时,如果左键被碰撞,将改变其值为真。
下一步,我将要求SPOT从3倒数到1。我拖放了另外三个声音模块到程序中。图18-14显示了这三个声音模块及最后一个声音模块的配置面板。

图18-14  SPOT将从3倒数到1

当倒数结束后,我们应该在LCD屏幕上显示“Pressed”或者“Not Pressed”。为了完成这一点,我们又将拖放另一个变量模块。这次我还是将选择我创建的变量Pressed,但这次我将动作部分改为读取(见图18-15)。

图18-15  开关模块将读取变量Pressed的值
现在,我拖放了一个开关模块并配置它读取逻辑值(见图18-16),我关闭了平面视图,因此开关模块能看到选项卡形式。我同时从具有真或假值的变量模块连接了一根数据线到开关模块。我还在开关模块的真选项卡内放置了一个显示模块,并配置它显示“Pressed”(在图18-16中没有显示其配置面板,但这是很容易做到的)。

图18-16  如果变量值为真,显示模块将显示“Pressed”

在假选项卡内我放置了另外一个显示模块,该模块清除LCD屏幕,并显示“Not Pressed”(图18-17)。

图18-17  如果变量值为假,显示模块将显示“Not Pressed”

最后,我拖放了一个NXT按钮等待模块来等待右键按下,这将给我时间来看到屏幕上的结果(见图18-18)。

图18-18  如果我按下右键,程序将停止

现在运行程序,多尝试几次——当数数结束后,立即按下左键,或者不按左键。你按左键或不按左键的决定将转换为一个真或假的值并写入变量Pressed。当倒数结束后,开关模块读取变量Pressed的值,其相应的文本将显示在LCD屏幕上。
变量对你的机器人存贮信息是一种非常有用的方法,这些信息可以在随后使用。一旦变量被创建并且有数据写入,数据可以在你想要的任何时候得到。——不错在程序结束前。如果你想保存数据到程序结束和/或者关机后,你需要另外一个类型的模块,这就是常量模块显得有用的地方。
常量模块
当你在程序中使用变量模块,任何变量值(数字,文本或者逻辑值)都只在程序运行过程中被保存,一旦程序结束,你的变量值也就消失了。通常这不是大问题。你给机器人的典型编程只是在程序运行过程中使用变量。
但是如果有个值经常变化,且在你上传给机器人的多个程序中使用时该怎么办?例如,让我们假设一个程序(程序1)让机器人在离终点线12英尺的地方停止,且需要在停止前跳一点舞。我们假定从起点线到终点线的原始距离为24圈,程序1可以指示机器人通过移动模块向前转动20圈(离终点线还有4圈)后,在其跨过终点线之前停止,然后跳一段舞后结束。
我们同时假设另一个程序(程序 2)要求机器人在跳舞之前向前转过起点线到终点线一半的距离;你将编程添加一个移动模块并配置为向前转动12圈,当机器人到达这一位置后停止,跳一段舞,然后继续向终点线移动。
最后,我们还有第三个程序(程序3)要求机器人向前转过1/4的总距离也即6圈,然后跳一段舞,然后继续向前终点线移动。再一次,你可以在跳舞前配置移动模块向前转动6圈。
你可以很容易地完成这三个程序的编程,但是如果我改变起点线到终点线的距离为48圈,那将会怎么样呢?现在你不得不回到三个程序中(程序1,程序2和程序3)来修改一系列的移动模块的配置面板。
应该有更好的方法来保存程序间的重要数值……确实有方法,它称为常量模块。
如同变量模块一样,常量模块也能存贮一个单一的值——一个数字,一个逻辑值或者一串文本。这个值存贮在智能积木块内并被称为一个“全局常量”。只要你不删除程序,即使你关闭了智能积木块的电源,这个值还是保存在智能积木块上。因为它存贮在智能积木块上,你可以在其它程序中使用常量模块来读取存贮在智能积木块上作为常量的值。这是一个“全局”数据——它可以在任何地方使用(好吧,至少可以被存贮在智能积木块中任何程序使用)。
为了向你介绍它是如何工作的,我将创建一个新程序(命名为Distance),程序中创建了一个命名为“StartToFinish”的常量,这个常量的值等于起点线与终点线之间的距离(英寸)。图18-19显示了包含在这个程序中的单个模块。

图18-19  在Distance程序中的单个模块

在我使用这个常量模块之前,我必须要创建一个存贮起点线到终点线之间距离(以英寸为单位)的一个常量。为了完成这一点,我点击编辑菜单并选择定义常量选项,会弹出一个窗口如图18-20所示。

图18-20  创建一个常量来保存一个值以供其它程序使用
现在我需要给常量一个名字及其数据类型,点击创建按钮(见图18-20)并在名字字段内输入“StartToFinish”作为常量名,在数据类型下拉菜单中选择数字,并在数值部分输入一个值(这个例子中为24),如图18-21所示。

图18-21  为常量提供一个名字,数据类型及一个数值

点击确定按钮,然后点击关闭按钮结束常量编辑窗口。
现在点击你程序中的常量模块(见图18-19),并在配置面板中选择“从列表选择”选项,新建的常量StartToFinish将会出现在配置面板右边栏目的列表中,点击选中它,保存程序(命名为Distance)并上传到智能积木块。
现在可以创建程序1,该程序将使用存贮在常量StartToFinish的数值。我创建了程序1并拖放了常量模块,如图18-22所示。

图18-22  一个新程序的常量模块的配置面板

注意到在图18-22中,我可以简单的给常量输入一个名字,从下拉菜单中选择一个数据类型来定义一个新常量(而不用从编辑菜单中定义常量)。但是因为我已经配置了一个称为“StartToFinish”的常量并上传到了智能积木块,因此我选择了“从列表选择”选项,如图18-22所示。当我选择该选项后,在配置面板的右侧将会出现可以使用的常量列表,如图18-23所示。

图18-23  从列表中选择常量

如果你还记得,程序1的功能是让机器人在跳舞前,向前转动全程距离少4圈的路程。在我们知道常量模块之前,我们就简单的放置一个移动模块并配置它向前转动20圈。
但现在,我们可以使用常量模块(具有值24)与运算模块进行计算。我将在第20章详细介绍运算模块,不过现在只需要知道运算模块可以作加,减,乘等运算。图18-24显示了我使用运算模块从常量模块取数(24)并减去4。我首先从常量模块连根数据线到运算模块的输入接头A,同时我使用运算模块的配置面板设置B值为4,运算部分设置为执行减法运算。这样将把从A减去B后的值提供给移动模块。

图18-24  常量模块将其值提供给运算模块

然后,我拖放了一个移动模块并配置为圈数,然后从运算模块连根数据线到移动模块的持续时间数据接头。其配置如图18-25所示。

图18-25  移动模块将从运算模块得到它的持续时间值

现在剩下的就是拖放几个移动模块让机器人进行跳舞,最后再转动4圈至终点线(我将其留给你去编程完成——按你喜欢编个简单的舞或者复杂的舞。)
对程序2,你可以创建一个类似的程序,但可以使用运算模块将常量模块提供的数值除以2(取半),并将其结果发送给移动模块。程序3使用运算模块将常量模块值除以4,并将其结果发送给移动模块。(全程距离的1/4)。
因此,为什么不只简单的使用一系列移动模块而要使用常量模块和运算模块呢?请考虑——如果我将起点线到终点线的距离改为48或者100,那将会怎样?对使用移动模块的程序来说,你必须打开所有三个程序(程序1,2及3)并改变特定移动模块中的值。
但现在我们有常量模块。现在我所需要做的只是打开名字为“Distance”的原始程序,并改变其值(24)为一个新距离,保存程序并上传到智能积木块并运行。现在常量已经改变,程序1,2和3不需要打开做任何修改。每个程序将采用存贮在常量StartToFinish的值并计算要移动的正确距离。是不是很酷,嗯?
变量对常量
决定何时使用变量模块及何时使用常量模块不应该会混淆。下面是帮助你决定什么时候使用他们的一些建议:
&#61599;        只在单个程序使用时采用变量模块来存贮数值。
&#61599;        给存贮在智能积木块上的多个程序提供一个确定值时使用常量模块。
&#61599;        当运行单个程序并需要改变值时使用变量模块。
&#61599;        当运行多个程序并不需要改变值时使用常量模块。
请记住,常量模块同样可以提供文本及逻辑数据值。你可以简单地编写一个常量模块来记住你的名字(文本)并在每个程序运行时显示在LCD屏幕上。当某人运行一个程序时,它可以显示“由YOUR NAME编程”,其中YOUR NAME由存贮在智能积木块上的常量模块提供。
同样,常量模块也可以拥有一个给你经常使用的比较模块的逻辑真值。(请参见前面第15章)。当与这个常量值进行与运算时,只有第二个真值才能让比较模块产生一个真的输出结果。
当给你的机器人进行编程时,变量及常量是要理解的非常重要的概念。如果你想搭建并编写一个复杂程序的机器人,你必须理解变量及常量模块,你对使用它们掌握得越透彻,你可以给你的机器人更好的决策能力。
下一步内容?
在下一章,我将给你介绍如何使用文本模块。它是给LCD屏幕提供信息的简单方法,包括指令及其测试你机器人性能的结果。文本模块提供一些格式及其对文本的组合,以给你对如何显示文本的一些控制。
图18-1.JPG
图18-2.JPG
图18-3.JPG
图18-4.JPG
图18-5.JPG
图18-6.JPG
图18-7.JPG
图18-8.JPG
图18-9.JPG
图18-10.JPG
图18-11.JPG
图18-12.JPG
图18-13.JPG
图18-14.JPG
图18-15.JPG
图18-16.JPG
图18-17.JPG
图18-18.JPG
图18-19.JPG
图18-20.JPG
图18-21.JPG
图18-22.JPG
图18-23.JPG
图18-24.JPG
图18-25.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2013-1-1 15:07:11 | 显示全部楼层
谢谢付出!2013努力!新年快乐!
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-1 20:38:02 | 显示全部楼层
同乐同乐!
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-6 18:54:23 | 显示全部楼层
本帖最后由 James.Yang 于 2013-1-6 18:56 编辑

第19章 基本文本
对处理文字的章节,将不会太长,你看,甚至也介绍也很简短。你将学习到使用文本模块来给你的机器人将文本组成句子,将字母组成单词。
文本模块
Mindstorms NXT机器人可以使用声音模块产生许多声音。然而,如果你想让机器人来控制书面文字,你必须理解文本模块及知道如何正确使用它(如图19-1)。

图19-1  文本模块及其配置面板

现在又有一个编程术语要添加到你的列表中:字符串(我的意思不是说你用于放风筝的绳子 )。
“字符串”是在程序生命周期内使用的项目,且非常容易定义。一串字符串是字母,数字,空格,特殊字符及其他们的任何组合的集合。以下是5个字符串的例子:
&#61599;        THISISASTRINGOFTEXT
&#61599;        So is this.
&#61599;        123456789
&#61599;        !@#$%^&*()
&#61599;        These are all strings, including this one
我向你介绍字符串的概念的原因,是因为文本模块具有可以将最多3个字符串组合成一个更长字符串值的能力。
让我们再看一下图19-1,文本模块可以拥有三个字符串值:A,B和C。注意所有三个字符串都可以通过配置面板人工输入(通过你,编程者)或者通过输入数据接头提供给文本模块。同时也要记住,字符串值A总是最左边,B在中间,C在最右边。你不能改变三个字符串组合的顺序。
作为一个示例,请看图19-2.

图19-2  文本模块的三个字符串

对字符串A的值,我在文本框内输入“I”,没有空格,字符串B的值包含“ am”(前面有空格),字符串C的值是“ SPOT”(前面有空格)。前面的空格是为了在屏幕上显示时,不要让组合的文本看起来象“IamSPOT”,而是看起来应该为“I am SPOT”。一旦文本组合好后,如何将新文本显示在屏幕上呢?你首先得添加一个显示模块来将文本显示在屏幕上(如图19-3)。然后从文本模块的输出文本数据接头连接数据线到显示模块的输入文本数据接头。输出文本数据接头将提供A,B,C的组合文本。

图19-3  三个字符串组合后输送给显示模块
接下来,添加一个时间等待模块,这样你可以在程序结束,文本消失前看到文本。你要配置等待模块等待10秒钟(如图19-4)。

图19-4  等待模块将给你时间来看到屏幕上显示的结果

当程序运行时,LCD屏幕上会显示“I am SPOT”。在第18章,我已经给你介绍了如何使用变量模块,你可以使用该模块通过输入数据接头(A,B或C)给文本模块发送文本。要完成这一点,你要配置3个变量模块,每个模块将具有一个文本,从每个变量模块引出数据线到输入接头A,B,C,然后由文本模块完成剩下的内容。
练习19-1:字符计数
下面是一个简短的练习。使用文本模块将3个分开的字符串组合来创建一个程序,每个字符串具有10个字符的长度。通过将组合起来的字符显示在LCD屏幕上,使你很容易数出每一行能显示的最大字符个数。
这个练习的信息对需要将多少个字符挤在一行上时是非常有用的。我在本章的结尾放置了一个可能的解决方案。
下一步内容?
继续到下一章,我将介绍怎样编程让你的机器人具有一些基本的运算技能。信不信由你,你的机器人越是变得复杂,它越是可能需要执行一些加、减,甚至是乘或除运算。你的机器人本身不够聪明来作运算,因此它需要一个特殊的模块来帮助它执行计算。
练习解决方案
图19-5到图19-13显示了练习19-1完整的程序及配置面板。注意我将显示模块配置为从X=1的位置开始显示其接受到的任何文本。这将把任意字符串的第一个字符显示在LCD屏幕的最左边。我同时也创建了三个变量(String1,String2,String3)。参见第14章关于创建变量的指导,每个变量对应于一个变量模块。
前三个变量模块的动作部分被设置为写入,这样我可以输入字符串文本。接下来的三个变量模块(与文本模块连接)的动作部分被配置为读取,这样存贮在里面的数据可以被文本模块读取。(尝试将文本模块与最前面的三个变量模块相连——你将会看到,一个配置为写入的变量模块不能通过它的输出数据接头提供数据。)

图19-5  完成的程序及第一个变量模块的配置面板


图19-6  第二个变量模块的配置面板


图19-7  第三个变量模块的配置面板


图19-8  第四个变量模块的配置面板


图19-9  第五个变量模块的配置面板


图19-10  第六个变量模块的配置面板


图19-11  文本模块的配置面板


图19-12  显示模块的配置面板


图19-13  NXT按钮等待模块的配置面板
图19-1.JPG
图19-2.JPG
图19-3.JPG
图19-4.JPG
图19-5.JPG
图19-6.JPG
图19-7.JPG
图19-8.JPG
图19-9.JPG
图19-10.JPG
图19-11.JPG
图19-12.JPG
图19-13.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2013-1-9 07:59:05 | 显示全部楼层
兄弟高手啊,继续努力啊。
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-9 19:39:56 | 显示全部楼层
我是新手,共同学习
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-9 19:40:38 | 显示全部楼层
本帖最后由 James.Yang 于 2013-1-9 19:41 编辑

第20章 基本运算
你不是很喜欢简短的章节吗?好吧,我保证这又是非常简短的一章。因此准备在你的工具集中再添加一个编程模块——你将使你的机器人变成一个计算器。
运算模块
你的机器人可以作一些非常简单的运算:加、减、乘和除。请看图20-1,它显示了运算模块及其配置面板。

图20-1  运算模块及其配置面板

运算模块使用两个值:A和B。对NXT-G 1.0的用户,这此数值可以是正整数或负整数。一个整数指整个数字没有小数点的数值。如果你试着输入一个数如-4.3或者10.8,运算模块就会自动取整至与其最接近的整数(上述的例子取整为-4和11)。但对NXT-G 2.0的用户来说,已不受限于整数运算,小数也被接受了。
在操作部分,有个下拉菜单给你选择要执行的运算类型。如果你点击下拉菜单,你将看到以下选项:
&#61599;        加法:这个选项将进行A+B运算。
&#61599;        减法:这个选项将进行A-B运算。
&#61599;        乘法:这个选项将进行A×B运算。
&#61599;        除法:这个选项将进行A÷B运算。
&#61599;        取绝对值:这个选项将对A取绝对值。
&#61599;        平方根:这个选项将对A进行平方根运算。

注意:NXT-G 1.0没有取绝对值及平方根运算的能力。


注意在图20-1中我已打开了运算模块的数据中心,它有两个输入数据线接头(一个给数值A,另一个给值数B)及三个输出数据线接头。运算模块需要一个或两个整数值,这取决于你在操作部分选择的选项:如果A或者B为空,其默认值为0,而绝对值与平方根运算除外,它们仅需要一个数值A。
数字可以在配置面板中人工输入A值及B值,或者通过给接头A及接头B连接数据线以提供给运算模块数值(见图20-2)。

图20-2  运算模块可以通过数据线为数值A和数值B接收数据

图20-2显示了通过创建两个随机数(由两个随机模块产生)的程序例子。每个随机模块通过其输出数据接头连接数据线到运算模块的A和B输入数据接头。
你必须理解如果你不打开运算模块的数据中心,你将不能对运算模块做任何事情,这是因为:不管你选择对数值A和数值B进行了何种运算(加、减、乘还是除),其结果只能从结果数据接头得到(通过数据线)。
一旦数值A和数值B相加后,你想在LCD屏幕上看到其结果。而要做到这一点,你首先必须将数字转化为文本,拖放一个数字转文本模块(见图20-3),并从运算模块的结果数据接头连根数据线到数字转文本模块的数字数据接头。

图20-3  数字转文本模块将数字答案转化为文本

为了让你在LCD屏幕上看到结果,你从数字转文本模块的文本数据接头连接数据线到显示模块的文本数据接头,如图20-4(记得将显示模块改变为显示文本)。同时,添加一个小小的等待模块,这样在结果从屏幕上消失前你有时间看到它。

图20-4  显示模块将在LCD屏幕上显示结果
练习20-1:计算转动的总角度数
编程让你机器人转动随机的角度数,这个随机数应该在-360与-1之间(负数)。当运动结束后,用相同的范围产生另一个随机数,并让机器人转动这个角度数。在屏幕上以正数显示转动的总角度数。比较你的方案与我在本章结尾处提供的方案。
下一步内容?
这就是运算模块!记住,数值A和数值B必须为正整数或负整数,如果你不给他们配置初值,其默认值为零(0)。如果你打算显示运算模块运算的结果,在发送给显示模块之前,你必须将数字转换为文本。很有意思!下面我将介绍如何阻止你的机器人打嗑睡。
练习解决方案
图20-5到图20-14显示了练习20-1完整的程序和所有模块的配置面板。注意随机模块产生的数字为负值,这些数字发送给移动模块之前先发送给运算模块进行绝对值运算。

图20- 5  完整的程序及第一个随机模块的配置面板


图20-6  第一个运算模块的配置面板


图20-7  第一个移动模块的配置面板


图20-8  第二个随机模块的配置面板


图20-9  第二个运算模块的配置面板


图20-10  第二个移动模块的配置面板


图20-11  第三个运算模块的配置面板


图20-12  数字转文本模块的配置面板


图20-13  显示模块的配置面板

图20-14  NXT按钮等待模块的配置面板
图20-1.JPG
图20-2.JPG
图20-3.JPG
图20-4.JPG
图20-5.JPG
图20-6.JPG
图20-7.JPG
图20-8.JPG
图20-9.JPG
图20-10.JPG
图20-11.JPG
图20-12.JPG
图20-13.JPG
图20-14.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-13 16:13:20 | 显示全部楼层
本帖最后由 James.Yang 于 2013-1-13 16:14 编辑

第21章 保持清醒
又是一个简短章节?当然!你可以学习一些东西,然后回头对你的NXT机器人进行一些练习。但是如果你的机器人沉睡的话,你不能练习太多。本章将告诉你如何让你的机器人保持工作,即使在智能积木块上的睡眠选项设置了2分钟或5分钟的简短休息时间。
保持活动模块
你的NXT机器人有个内置的特性,就是机器人在经过一段时间后会自动关闭。这个睡眠定时器由智能积木块进行配置,你可以选择在2,5,10,30或60分钟的休眠状态后关闭智能积木块,或者选择永不关闭。
睡眠定时器是一个有用的特点,你必须明确地设置一个合理的时间。它可以在你不小心忘记关闭智能积木块时帮助保存电力。例如:当一个程序执行完毕,机器人停止移动时,你已经离开一会了,睡眠定时器能够确保你的机器人自动关闭。但是,例如,如果你想创建一个机器人通过其超声波传感器来检测门的运动时该怎么办呢?想象一个房间报警系统要防止你兄弟姐妹的噪音对指令的干扰。如果你编程让机器人坐在门口并检测门的运动,你可以简单地将睡眠设置为永不关闭,这样机器人就不会自动关闭。然而,一个更简单的方法是使用保持活动模块。
保持活动模块及其配置面板如图21-1所示。

图21-1  保持活动模块及其配置面板

注意到其配置面板为空白!保持活动模块没有任何设置要进行配置。
以下是它的工作原理:在你的程序执行过程中,在任何时候执行保持活动模块,睡眠定时器将被复位到原始的开始时间。因此,如果你配置了智能积木块5分钟的睡眠定时器,而在程序运行1分钟后碰到保持活动模块,睡眠定时器将被复位到5分钟。
现在,为了使之有效,你可能需要在经常执行的地方放置一个保持活动模块。最佳放置保持活动模块的地方是循环模块,它经常会(或者连续)执行其内部的模块,包括保持活动模块。这是一种连续复位睡眠定时器的方法。(记住,睡眠定时器在你打开智能积木块时开始计时,但在运行程序时被复位。如果你没有运行程序,且将睡眠定时器设置为2分钟,那么经过120秒钟后,智能积木块将自行关闭。)
一个例子如图21-2所示。

图21-2  在循环模块内加上一个保持活动模块,就可以重复复位睡眠定时器

在这个简单的程序中,机器人将旋转几圈,说:“Hello”,然后一遍又一遍的重复……,如果触摸传感器按钮被按下,开关模块将执行保持活动模块来复位睡眠定时器。如果按钮一直没有被按下,机器人在默认的睡眠定时器时间到达时最终还是会关闭(假设睡眠定时器没有被设置为永不关闭)。
这一点很重要:在运行程序前,要经常检查智能积木块上的睡眠定时器的设置。一旦超过时间,程序将停止。这种情况经常会发生在睡眠定时器设置为2分钟或5分钟时的情况下,因此在运行程序前要再次检查确认,确保设置的睡眠定时器时间要长于你希望程序运行的时间。
在结束本章之前,我要提到的关于保持活动模块的最后一项内容就是,保持活动模块在其数据中心有一个输出数据接头,这个接头仅提供数字数据类型,其值为睡眠定时器以毫秒为单位的默认值(1000ms=1s)。你也许会发现这个数据接头没有多大用处,但它可以作为比较模块的一个输入来检查两个值的大小——智能积木块三个内部定时器之一的值与默认睡眠定时器时间值哪个值更大。根据比较模块的条件,在机器人使用停止模块关闭之前将会执行一些最终的动作,或者如前面提到的它可能会执行保持活动模块来复位睡眠定时器值。
由于某些原因,许多人不相信我所说的当睡眠定时器时间到达时,智能积木块将会简单地关闭。练习21-1是测试这句话的有效性的一个小程序例子。如果你需要帮助,我在本章结尾包含了一个简单的程序例子。
练习12-1:无限循环还是睡眠?
创建一个程序来检测智能积木块即使在运行一个死循环程序时,是否会在2分钟后自动关闭。确保将你的智能积木块的睡眠定时器设置为2分钟。
下一步内容?
不错,这就是保持活动模块。下一章第22章将是文件访问模块。你将学习到如何编程让机器人保存数据到文件,并且可以在现在或将来任何时间访问它。
练习解决方案
在你运行程序之前,确保智能积木块的睡眠定时时间设置为2分钟。要完成这一点,打开智能积木块,使用左右键来浏览设置选项并按回车键(橙色键)。再次使用左右键来浏览睡眠选项并按回车键。使用左右键顺数或倒数来改变屏幕上的值为2(选项包括2,5,10,30,60和永不)。
图21-3到图21-7显示了测试练习21-1的完整程序和配置面板。注意其循环模块被配置为无限循环。当程序运行时,智能积木块首先将发出一些声音,等待3秒钟,转动电机B和C一圈,等待3秒钟,然后重复整个过程。使用一个秒表或者定时器来证实当程序运行开始120秒钟后,智能积木块关闭。

图21-3  完整的程序和循环模块的配置面板


图21-4  声音模块的配置面板

图21-5  第一个等待模块的配置面板


图21-6  移动模块的配置面板


图21-7  第二个等待模块的配置面板
图21-1.JPG
图21-2.JPG
图21-3.JPG
图21-4.JPG
图21-5.JPG
图21-6.JPG
图21-7.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2013-1-13 21:50:06 | 显示全部楼层
辛苦了!
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2013-1-14 19:14:41 | 显示全部楼层
本帖最后由 James.Yang 于 2013-1-14 19:33 编辑

第22章 你自己的文件柜
在第18章,我向你介绍了怎样使用变量模块和常量模块来保存数字和文本数据,但是对变量模块而言有个问题,一旦程序结束,其数据立即消失!甚至更糟的是,如果电池用光或者在程序运行时,你的机器人电源被关闭,变量模块将失去其拥有的任何数据。常量模块通过创建一个能够给多个程序使用的全局变量解决了这个问题,但是你必须通过定义常量菜单选项(见第18章)或者通过常量模块配置面板预先创建常量及其给其赋值。常量模块的另一个限制是模块能拥有的数据数量。
幸运的是,你的NXT机器人可以访问一个模块,该模块在内存中能够拥有很多数据,并且这些数据不必预先定义,这个模块就是文件访问模块。它允许你将数据存贮在一个文本文件中,该文件不会消失——即使你关闭机器人的电源或者程序运行结束。你的数据存贮在一个文件中并保存在NXT智能积木块的内存中,除非你删除它,它将一直存贮在那儿,就如同你的程序一样。
文件访问模块导入
文件访问模块及其配置面板如图22-1所示。

图22-1  文件访问模块及其配置面板

现在,在我向你介绍怎样使用该模块之前,先让我介绍一些在使用文件访问模块时你必须要遵守的简单规则:
规则1:该模块只能拥有数字或文本数据,不能有逻辑数据。
规则2:该模块可以执行四种操作:读取、写入、关闭和删除。
规则3:每个文件访问模块只能执行四种操作之一,也即意味着对每个操作        类型你必须使用一个文件访问模块。
规则4:当你向一个文件写入数据时,新添加的数据将追加在文件中任何已有的数据后面。
假设文本数据文件存贮有以下数据:15429823,现在,如果你添加34到文件后会发生什么?不错,根据规则4,文件现在将拥有1542982334。34将追加到最后。
还有一些规则需要你记住:
规则5:为了读取写入文件的数据,你首先必须关闭文件。
规则6:要覆盖文件(但要保持相同的文件名),你必须删除文件,然后创建一个相同名字的文件。
文件访问模块确实需要一些实验来学习如何正确的使用它。我非常鼓励你来执行下面的例子,然后试着做些改变。尝试读取一些混合数据(数字和文本类型)。然后,关闭文件且尝试再次打开它,读回你的数据。通过对模块的尝试,你会非常快的指出对你的机器人来说使用文件访问模块是多么的好。
但现在,让我先介绍怎样使用这个模块的基础知识。
我们首先从配置面板的动作部分开始,动作部分具有一个拥有四个选项的下拉菜单:读取,写入,关闭和删除,非常简单——选择读取选项来读取文件的内容;选择写入选项将数据写入文件;选择关闭选项来关闭文件;选择删除选项来删除文件。
名字部分是指定你将要处理的文件名字(你可以写入,读取,关闭或者删除它)。如果你在创建一个新文件,名字要尽量简短及唯一但应该描述清楚以便于你能记住文件所包含的数据类型。比较好的例子,“RightTurns”(它可以存贮机器人右转圈数的总和)和“TeamName”(它可以存贮给不同程序使用的一个团队名字)。
文件部分将列出已连接且与软件进行通讯的智能积木块上所有已存在的文件,你可以从列表中选择一个文件而不用指定一个新文件名。
类型部分有一个具有两个选项的下拉菜单:数字和文本。选择数字选项将创建一个数字部分,让你可以输入数值或者使用小按钮来增加或降低数值(如果你是在写入文件)。选择文本选项将创建一个文本部分,让你可以输入一些文本(同样假设你是在写入文件)。
如果你是在读取文件,你必须指定你是从文件中读取数字还是文本值。例如,如果文件包含1234,你选择读取文本值,数据将会按文本处理而不是按数字处理。要记住,一定要记得选择合适的数据类型来读取或者写入文件。
如果你是在关闭文件,这就简单地保护了文件被改写或者删除。当你结束一个文件使用,在打开一个不同的文件之前,要养成关闭文件的良好习惯。
让我给你一个使用文件访问模块的程序小例子。
首先,我将创建一个名字为LuckyNumber的新文件,如图22-2所示。选择15作为写入文件的数字数值。


图22-2  创建一个新文件

当数字写入文件后,你必须关闭文件,这将使你可以在随后读取数据。因此再添加一个文件访问模块来关闭文件(如图22-3)。

图22-3  关闭文件将允许你随后读取文件

现在,下面给SPOT一些伪代码:
[我]:SPOT,我在你的内存中保存了一个叫做LuckyNumber的文件,我想让你向前移动3圈,然后在LCD屏幕上显示我的幸运数。
下面是将看到的程序样子。首先拖放一个移动模块让SPOT向前移动3圈(如图22-4)。

图22-4  向前移动3圈

现在,你需要读取存贮在文件LuckyNumber中的数值并让SPOT将该值显示在LCD屏幕上。幸运的是,你可以使用数字转文本模块来将数字转换为文本后输出给显示模块。因此,第一步将从文件中读取数值。这将通过拖放又一个文件访问模块并读取数据来完成(如图22-5)。

图22-5  读取存贮在文件中的值

现在,你需要拖放一个数字转文本模块,并配置为读取存贮在文件中的值。然后将该文本值传给显示模块。这个如图22-6所示,同时图中还包含一个最终的等待模块及其配置面板。

图22-6  读取存贮在文件中的值

要注意到有两个输出数据接头具有井号(数字)#标记。一个#标记是提供当前数据写入文件访问模块(模块被设置为写入),另一个#标记是用来从文件中读取数据。这听起来很混乱,但要记住你可以写入文件的数字或文本包含有很多数字或者很多字符串。如果一个文件访问模块被设置为读取,它将读取在文件中读取的第一位数据。拖放另一个文件访问模块并设置为读取将读取文件中的下一位数据。(你可以在一个循环模块中放置一个文件访问模块并设置为读取,每次循环就会读取文件中的下一个数字或者下一位文本)。
图22-6显示了从输出数据接头连接了一根数据线。当使用文件访问模块时要小心选取正确的数据接头,否则你会得到一根虚的数据线。当完成数据线后,文件访问模块将提供作为数据存贮的数值以供数字转文本模块读取。你可以自己测试它来证明其正确性。数字转文本模块将其结果传给显示模块;程序等待你按下左键(使用最后一个等待模块),然后程序结束。
文件访问模块是用来保存机器人在探路过程获得的数据的一个伟大方法。你可以使用文件来保存象电机转动圈数,左转及右转的次数等情况。你的机器人随后可以从这些文件中读取数据,这样机器人可以找到它回家的路。有很多种方法来使用你存贮在智能积木块上的文件,现在你已知道如何创建它们,添加数据及删除它们。
在我结束本章之前,我将提出一些有用的小帖士。首先是养成关闭文件的习惯,通过保存文件,你重置了文件,所有保存在文件中的数值将可以有序读取(从第一个到最后一个)。如果你在其它程序中使用文件访问模块,我建议你在程序的开头放置一个文件访问模块,并配置为关闭文件。再一次确保这个文件的数据能按正确的顺序读取。
记住,由于保存在文件中的数据是按顺序的,要读取另一个值只要简单地添加一个文件访问模块并设置成读取,或者你可以在循环模块内部放置一个文件访问模块,这样程序每次循环,文件访问模块将读取文件中的下一个值。
最后,必须记住文件有结尾。当文件到达其结尾处时,文件访问模块将不能读取任何值。为了测定是否到结尾,文件访问模块有个非常有用的错误数据接头,它将返回一个真或假的数值(这将使用数据接头而不是在实际文件中存贮的真或假值)。你可以从错误数据接头连接一个数据线作为一个监测条件。例如,循环模块可以被配置为当其接收到来自错误数据接头的真值时,中止循环——循环中止,程序继续。
本章仅是对文件访问模块强大的功能作了蜻蜓点水般的介绍。相信我,这个模块还有其它更多用处,你将会发现给你的机器人有记录数据(随后可以恢复数据)的能力将是一个非常有用的工具。你可以使用它来追溯光线值,左转和右转次数,等等。多多练习文件访问模块来学习一些技巧将给你的机器人长期的记忆!
练习22-1:左,右,左
为SPOT创建一个程序产生5个系列的随机转弯,左或右,在每两次转弯之间停顿几秒。记下左转的次数,将左转次数写入存贮在智能积木块的一个文件中以供后面使用,同时,在程序结束前在LCD屏幕上显示存贮在文件中的数值。
这个练习将测试你已经学习过的多种NXT-G模块,包括变量模块,循环模块,开关模块和运算模块。如果你有问题,我在本章结尾包含了一个可能的解决方案。
下一步内容?
下一步,将要使用校准模块来确保你的光线及声音传感器能正常工作。我发现,这个模块并没有按其应该有的频率经常使用,与这些传感器相关的许多错误经常与一个事实相关,就是设置为一种条件(例如一个明亮的房间)的触发,而机器人及程序会执行在另外一个条件下(例如稍稍明亮的房间)。校准模块能够帮助消除这些不一致的情况。
练习解决方案
由于练习22-1非常长,我将提供一些额外的讨论来解释我为什么要用这个模块。图22-7到图22-22为练习22-1提供了完整的程序及配置面板。

图22-7  前半个程序及变量模块的配置面板
变量模块原始数据设置为0,这个变量用来保存程序执行过程中左转的次数。

图22-8  循环模块后面的后半个程序


图22-9  循环模块的配置面板


图22-10  随机模块的配置面板

因为我想要随机的左转或右转,因此我将配置随机模块产生两个数字——1或者2。随后我将在开关模块中使用这个数值。

图22-11  开关模块的配置面板

记得要将开关模块设置为数字类型且为1和2两个可能的条件改变默认值。(参见第12章关于开关模块的配置信息。)

图22-12  条件2的移动模块的配置面板

开关模块将从随机模块取得数字(1或2)并使用该数字来选择路径。条件2将使电机右转,条件1将使电机左转。注意在图22-7中我们看不到条件2的移动模块,该图只显示了开关模块条件1的选项卡。

图22-13  条件1的移动模块的配置面板

这个移动模块将使机器人左转,除了这个移动模块,还需要其它一些模块来追溯机器人左转的次数。

图22-14  第二个变量模块的配置面板

这里将把存贮在变量模块中的现有值传送给运算模块。

图22-15  运算模块的配置面板

运算模块将存贮在变量模块中的数值加1,每当条件1执行时,存贮的数值加1。

图22-16  第三个变量模块的配置面板

当数值加1后,必须将其重新写入变量模块。注意在图22-16中这个变量模块设置为写选项。

图22-17  等待模块的配置面板


图22-18  第四个变量模块的配置面板

当循环结束后,存贮在变量模块中的数值必须写入文件访问模块,因此将此变量模块设置为读取。

图22-19  文件访问模块的配置面板


图22-20  数字转文本模块的配置面板


图22-21  显示模块的配置面板


图22-22  等待模块的配置面板
图22-1.JPG
图22-2.JPG
图22-3.JPG
图22-4.JPG
图22-5.JPG
图22-6.JPG
图22-7.JPG
图22-8.JPG
图22-9.JPG
图22-10.JPG
图22-11.JPG
图22-12.JPG
图22-13.JPG
图22-14.JPG
图22-15.JPG
图22-16.JPG
图22-17.JPG
图22-18.JPG
图22-19.JPG
图22-20.JPG
图22-21.JPG
图22-22.JPG
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 马上注册

本版积分规则

手机版|中文乐高 ( 桂ICP备13001575号-7 )

GMT+8, 2024-11-21 16:42 , Processed in 0.101807 second(s), 20 queries .

Powered by Discuz! X3.5

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表