nop*_*ole 67 ruby global-variables
我有一个看起来像这样的程序:
$offset = Point.new(100, 200);
def draw(point)
pointNew = $offset + point;
drawAbsolute(point)
end
draw(Point.new(3, 4));
Run Code Online (Sandbox Code Playgroud)
使用$offset
看起来有点怪异.
在C中,如果我在任何函数之外定义某些东西,它会自动成为一个全局变量.为什么在Ruby中它必须$offset
但不可能offset
并且仍然是全局的?如果是offset
,那么它是本地的吗?但是本地到哪里,因为它感觉非常全球化.
是否有更好的方法来编写上面的代码?$offset
起初使用可能看起来有点难看.
更新:我可以将此偏移量放在class
定义中,但如果两个或多个类需要使用此常量呢?在这种情况下,我还需要定义一个$offset
吗?
Chu*_*uck 111
Ruby中的变量范围在某种程度上受到了sigils的控制.以$
全局开头的变量@
是实例变量的变量,@@
表示类变量,以大写字母开头的名称是常量.所有其他变量都是本地变量.当您打开一个类或方法时,这是一个新范围,并且前一个范围中可用的本地可用不可用.
我通常更愿意避免创建全局变量.有两种技术通常达到我认为更清洁的相同目的:
在模块中创建常量.因此,在这种情况下,您将把所有需要偏移的类放在模块中Foo
并创建一个常量Offset
,这样所有类都可以访问Foo::Offset
.
定义访问该值的方法.您可以全局定义方法,但我认为最好将其封装在模块或类中.这样,您可以在需要的地方获得数据,如果需要,您甚至可以更改数据,但程序的结构和数据的所有权将更加清晰.这更符合OO设计原则.
Igo*_*gor 53
你需要意识到的一件事是在Ruby中,一切都是一个对象.鉴于此,如果你没有在规定的方法Module
或Class
,红宝石将会把它的内部Object
类.因此,您的代码将在本地Object
范围内.
面向对象编程的典型方法是将所有逻辑封装在一个类中:
class Point
attr_accessor :x, :y
# If we don't specify coordinates, we start at 0.
def initialize(x = 0, y = 0)
# Notice that `@` indicates instance variables.
@x = x
@y = y
end
# Here we override the `+' operator.
def +(point)
Point.new(self.x + point.x, self.y + point.y)
end
# Here we draw the point.
def draw(offset = nil)
if offset.nil?
new_point = self
else
new_point = self + offset
end
new_point.draw_absolute
end
def draw_absolute
puts "x: #{self.x}, y: #{self.y}"
end
end
first_point = Point.new(100, 200)
second_point = Point.new(3, 4)
second_point.draw(first_point)
Run Code Online (Sandbox Code Playgroud)
希望这有点澄清.
mik*_*kej 10
其中一个原因全局变量需要一个前缀(的原因pointNew = offset + point
)是因为在Ruby中,与C,你没有给予类似的声明中分配给他们,所以没有特定的前缀为全局变量之前声明变量draw
的平局中然后Ruby不会知道你是在引用现有变量还是在方法中创建一个新的局部变量.与offset
实例变量的前缀相同.
归档时间: |
|
查看次数: |
124782 次 |
最近记录: |