简要解读Ruby面向对象编程中的作用域
技术  /  管理员 发布于 6年前   330
作用域
Ruby中不具备嵌套作用域(即在内部作用域,可以看到外部作用域的)的特点,它的作用域是截然分开的,一旦进入一个新的作用域,原先的绑定会被替换为一组新的绑定。
程序会在三个地方关闭前一个作用域,同时打开一个新的作用域,它们是:
上面三个关键字,每个关键字对应一个作用域门(进入),相应的end则对应离开这道门。
扁平化作用域
从一个作用域进入另一个作用域的时候,局部变量会立即失效,为了让局部变量持续有效,可以通过规避关键字的方式,使用方法调用来代替作用域门,让一个作用域看到另一个作用域里的变量,从而达到目的。具体做法是,通过Class.new替代class,Module#define_method代替def,Module.new代替module。这种做法称为扁平作用域,表示两个作用域挤压到一起。
示例代码(Wrong)
my_var = “Success”class MyClass puts my_var #这里无法正确打印”Success” def my_method puts my_var #这里无法正确打印”Success” endend
示例代码(Right)
my_var = “Success”MyClass = Class.new do puts “#{my_var} in the class definition” define_method :my_method do “#{my_var} in the method” endend
在一些语言中,比如java或C#,有内部作用域(inner scope)的概念。在内部作用域可以看到外部作用域(outer scope)中的变量。但ruby中没有这种嵌套式作用域的概念,它的作用域是截然分开的,一旦进入一个新的作用域,原先的绑定就会被替代为一组新的绑定。
在ruby中,程序会在三个地方关闭前一个作用域,同时打开一个新的作用域:类定义、模块定义、方法。
只要程序进入类、模块或者方法的定义,就会发生作用域切换。这三个边界分别用class,module和def关键字作为标志,每一个关键字都充当了一个作用域门(scope gate)。
怎样让绑定穿越一个作用域门呢?比如下面的代码:
my_var = “hello”class MyClass #你希望在这里能打印my_var def my_method #...还有这里 endend
在进入另一个作用域时,局部变量会立刻失效。如果把class关键字替换为某个非作用域门的东西,比如方法,就能在一个闭包中获得my_var的值,并把这个闭包传递给该方法。代码如下:
my_var = “hello”MyClass = Class.new do puts “#{my_var} in the class definition” def my_method #...这里怎样打印出来呢? endend
用Module#define_method()方法可以替代def,代码如下:
my_var = “hello”MyClass = Class.new do puts “#{my_var} in the class definition” define_method :my_method do puts “#{my_var} in the method” endend MyClass.new.my_method
hello in the class definitionhello in the method使用方法来替代作用域门,可以让一个作用域看到另一个作用域中的变量,这种技术可以称之为“扁平作用域”。
共享作用域
将一组方法定义到,某个变量的扁平作用域中,可以保证变量仅被有限的几个方法所共享。这种方式称为共享作用域。
122 在
学历:一种延缓就业设计,生活需求下的权衡之选中评论 工作几年后,报名考研了,到现在还没认真学习备考,迷茫中。作为一名北漂互联网打工人..123 在
Clash for Windows作者删库跑路了,github已404中评论 按理说只要你在国内,所有的流量进出都在监控范围内,不管你怎么隐藏也没用,想搞你分..原梓番博客 在
在Laravel框架中使用模型Model分表最简单的方法中评论 好久好久都没看友情链接申请了,今天刚看,已经添加。..博主 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 @1111老铁这个不行了,可以看看近期评论的其他文章..1111 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 网站不能打开,博主百忙中能否发个APP下载链接,佛跳墙或极光..
Copyright·© 2019 侯体宗版权所有·
粤ICP备20027696号