发布于 2016-01-23 11:04:05 | 134 次阅读 | 评论: 0 | 来源: 网友投递
Ruby编程语言
Ruby,一种为简单快捷的面向对象编程(面向对象程序设计)而创的脚本语言,在20世纪90年代由日本人松本行弘开发,遵守GPL协议和Ruby License。它的灵感与特性来自于 Perl、Smalltalk、Eiffel、Ada以及 Lisp 语言。
return,break,next 这几个关键字的使用都涉及到跳出作用域的问题,而他们的不同 则在于不同的关键字跳出去的目的作用域的不同,因为有代码块则导致有一些地方需要格外注意。
return
常用方式
通常情况下的return语句和大家理解的意思是相同的。
def m1 param
if param == 1
return 'returned 1'
end
'returned default value'#根据Ruby语言规范,最后一条执行语句的结果将作为返回值返回,retu rn是可 选的
end
m1(1) # => returned 1
m1(2) # => returned default value
def m1
'return default'
ensure
puts 'I am sure that it will be here!'
end
m1 # => return default
def m1
return 'return default'
ensure
return 'I am sure that it will be here!'
end
m1 # => I am sure that it will be here!
在有代码块干预的情况下,又会有所不同:
def m1
p 'start ... '
proc do
p 'block start'
return
p 'block end'
end.call
p 'end ... '
end
m1
# 输出结果:
#
# "start ... "
# "block start"
def m1
p 'start ... '
-> do
p 'block start'
return
p 'block end'
end.call
p 'end ... '
end
m1
# 输出结果:
#
# "start ... "
# "block start"
# "end ... "
break
先来看一个简单的小例子:
result = [1, 2, 3, 4, 5].map do |i|
i * 2
end
p result # => [2, 4, 6, 8, 10]
result = [1, 2, 3, 4, 5].map do |i|
break if i > 3
i * 2
end
# FLAG
p result
result = [1, 2, 3, 4, 5].map do |i|
break 'returned break' if i > 3
i * 2
end
p result # => "returned break"
def m1
p 'start in m1 ... '
m2 do # 代码块
p 'start in block in m1 ... '
p 'end in block in m1 ... '
end
p 'end in m1 ... '
end
def m2 &block
p 'start in m2 ... '
block.call
p 'end in m2 ... '
end
m1
# 输出结果:
#
# "start in m1 ... "
# "start in m2 ... "
# "start in block in m1 ... "
# "end in block in m1 ... "
# "end in m2 ... "
# "end in m1 ... "
def m1
p 'start in m1 ... '
m2 do # 代码块
p 'start in block in m1 ... '
break
p 'end in block in m1 ... '
end
p 'end in m1 ... '
end
def m2 &block
p 'start in m2 ... '
block.call
p 'end in m2 ... '
end
m1
# 输出结果:
#
# "start in m1 ... "
# "start in m2 ... "
# "start in block in m1 ... "
# "end in m1 ... "
可以看到代码块的最后一行代码没有执行,m2的最后一行也没有执行,就是因为这一行没有执行,导致 break的第二个例子中的map没有返回任何值。总结一下,代码块中的break会直接跳出调用的方法(m2), 而在声明代码块的方法(m1)中继续执行此方法(m1)中剩下的语句。
next
next关键字类似其他语言中的continue,它的工作方式基本和continue类似。
def m1
p 'start in m1 ... '
m2 do # 代码块
p 'start in block in m1 ... '
next
p 'end in block in m1 ... '
end
p 'end in m1 ... '
end
def m2 &block
p 'start in m2 ... '
block.call
p 'end in m2 ... '
end
m1
# 输出结果:
#
# "start in m1 ... "
# "start in m2 ... "
# "start in block in m1 ... "
# "end in m2 ... "
# "end in m1 ... "
result = [1, 2, 3, 4, 5].map do |i|
next if i > 3
i * 2
end
p result # => [2, 4, 6, nil, nil]
p result # => [2, 4, 6, "next", "next"] ```
对于return,在方法中,代码块中都可以使用,而break和next只能在代码块中使用(循环结构中 也可以使用,但是一般它也是用代码块的形式来表示),如果在方法中调用两者会提示语法错误,也就是:
def m1
return # OK
break # Invalid break, compile error (SyntaxError)
next # Invalid next, compile error (SyntaxError)
end
return 大部分情况下和其他语言无异,需要注意在ensure以及Proc和Lambda两种不同的 代码块中的细节问题。
break 在有方法嵌套调用中的代码块中需要注意,它总是返回到调用代码块方法的方法中(有点绕)。
next 最老实,基本不需要注意什么。
最后就是,不只是return能返回值,break和next都能返回值。