本帖最后由 taroxd 于 2014-6-24 06:42 编辑
吐槽start。
重要说明:以下内容并不算“入门”,不属于教程活动的范围之中。
教程活动仅需要对 self 的简单理解即可。
在这段脚本中,我们可以看到,同在Game_CharacterBase,pos_nt?方法内部直接使用了pos?方法,也就是说在同一个类(class)里面,方法之间的互相调用是可以直接实现的。这种嵌来套去的调用方式在VA-RGSS3的默认脚本里面可谓遍地都是。
这里还是从类的作用域(也是一个方法可以被使用的范围)开始讨论。
这一段解释非常不好。
这种隐式的方法调用并不一定要在同一个类或子类中,关键在于 self 的设定。隐式方法调用相当于对 self 调用这个方法。
比如说下面的例子。
class Person attr_accessor :name include Math end
class Person
attr_accessor :name
include Math
end
你注意到,我们调用了一些方法,分别是 attr_accessor 和 include。显然这个方法并不是在Person或者Person的父类中。
这是因为,在类定义中,self 指的就是这个类
我们翻阅Ruby文档,在 Module 类可以找到 attr_accessor 和 include 的定义。
于是,我们可以尝试
class Person self.attr_accessor :name self.include Math end
class Person
self.attr_accessor :name
self.include Math
end
什么?你说报错?我才不告诉你为什么呢~
于是,我们在写代码的过程中,有这些方式可以改变 self 的值……
啊,再讲下去就成元编程了。我们还是回到原来的问题。
pos_nt?方法内部为什么可以直接使用pos?方法?
因为:在方法的定义中,self 的值被设为方法的调用者(接收者)。
我们假设对 a 事件调用了 pos_nt? 方法
a.pos_nt?
我们根据方法的定义,可以将其解释为:
a.pos?(x, y) && !a的实例变量@through
我们注意到了这里的实例变量。实例变量访问的,其实也是 self 的实例变量。
我们也可以这么定义 pos_nt? 这是没有任何问题的。
class Game_CharacterBase def pos_nt?(x, y) self.pos?(x, y) && !@through end end
class Game_CharacterBase
def pos_nt?(x, y)
self.pos?(x, y) && !@through
end
end
我们继续:
class Person attr_accessor :name include Math def do_math puts "sin(π / 3) = #{sin(PI / 3)}" end def do_something do_math do_physics end end m5 = Person.new m5.name = '喵呜喵5' def m5.do_physics puts "#{name}在做物理" end m5.do_something
class Person
attr_accessor :name
include Math
def do_math
puts "sin(π / 3) = #{sin(PI / 3)}"
end
def do_something
do_math
do_physics
end
end
m5 = Person.new
m5.name = '喵呜喵5'
def m5.do_physics
puts "#{name}在做物理"
end
m5.do_something
在这个例子中,你可以看到,在 Person 类里面并没有定义 sin 和 do_physics。那为什么我们可以直接调用呢?
为什么之后 m5.do_physics 明显在类的作用域外,却可以直接调用方法 name 呢?
没错,一切都在于 self 的切换 。
所以说,“类的作用域“仅仅有切换 self,切换当前类,屏蔽局部变量的功能,和方法的调用没有任何关系!
同理,def 的作用域也是如此!
“切换当前类”是什么东西?我就不告诉你。
当我们不想要屏蔽局部变量的时候怎么办呢?这个时候就应该……咳咳我又要讲多了。嗯就这样吧。
最后:
我觉得我写的东西就是枯燥……所以才让你们写啦~~~
但是,这种错误还是少犯为好。 |