`

Proc、Block的区别与使用

    博客分类:
  • Ruby
 
阅读更多

  代码块,我的理解就是匿名方法,有点像Java中的匿名类一样,似乎用更贴切的说法叫闭包,一个我至今未接触过的东西。学习到代码块和代码块对象(Proc)的时候,看着很晕,一个代码块对象可以用lambda和->同时定义,与对代码块的错误理解纠结在一起,晕了一晚上。今天早上又找了些资料看看,最终才弄懂。写这篇文章的时候,使用的Ruby是1.9.2

 

  Block和Proc的区别就是Proc是Block Object,需要用call方法调用,而Block则不用。

 

1.  代码块的定义分为两种方式调用,一种是do end定义,适用于多行代码,一种是{}定义,适用于一行,两者没有优劣,只有习惯的不同,遵从这种文化吧。

    下面这个就是最简单的代码块示例:

 

5.times do |i|
  puts "No.#{i+1}"
end

 

   但是,如果你想在一个方法调用一个外部的代码块,如何做到呢?这个magic可以通过yield关键字来做到

 

 

def bye(name)
  puts "bye,#{name}"
  if block_given?
    yield
  end
end

bye("Steve Jobs"){puts "missing you "}

    代码块可以作为一个隐含参数,并且是最后一个,而且只能使用一个,来传递给别的方法,前面正常的参数要用括号起。像这个例子,我传递了一个打印“missing you”的代码块给方法bye,通过block_given?来判断是否传递了一个代码块过来,传过来的话,则用yield执行,如果不判断,而直接使用yield的时候,没传代码块是要报错的。其输出结果为:

bye,Steve Jobs
missing you 

 

2.Proc的使用

   Proc就是代码块对象,既然是对象,一旦定义,就可以多次使用了,Proc当然可以用new来创建,这个似乎并不常用,常用的倒是用lambda方法和符号->来定义

2.1 lambda方式

    在方法名lambda后面加上代码块即可,示例如下:

 

proc=lambda {|name| puts "hello,#{name}"}
proc.call 'theoffspring'
proc.call 'Mike'

  输出结果是:

hello,theoffspring
hello,Mike

   而且,作为对象,它可以作用参数传递给方法调用,个数不限,位置不限,这点克服了代码块来作为参数传递的局限性,如:

 

def test_proc_multi_params(name, proc, proc2)
  puts "#{name} is coming ,and he wants to..."
  proc.call
  proc2.call
end

test_proc_multi_params("the offspring", lambda { puts "eat potato" }, lambda { puts "and water melon" })

  输出结果:

the offspring is coming ,and he wants to...
eat potato
and water melon 

   不过 ,代码块可以通过在参数名前加个&来转换成代码块对象,但仍然只能有一个,且在方法参数列表的最后,如:

 

def test_converted_block(name,&action)
  puts "#{name} is "
  action.call
end

test_converted_block("the offspring") {puts "eating lunch"}

 

  输出:

the offspring is
eating lunch 

注意调用   test_converted_block的参数写法,挺特殊的,不得不承认

 

2.2 ->方式

   你只要把lambda出现的地方换成->就行了,哦,对了,这种方式在定义Proc参数的时候,要写到括号的外面,多个的话,以逗号分隔。

    如:

 

proc=-> name { puts "hello,#{name}" }
proc.call 'theoffspring'
proc.call 'Mike'
分享到:
评论

相关推荐

    Ruby中的block、proc、lambda区别总结

    在规则引擎中,Ruby 的闭包使用特别频繁,而且有 block,Proc和 lambda 等后几种形式的用法,很让人困惑。为了深入理解代码,再次认真学习了一下 Ruby 的闭包,特别是 block,proc 和 lambda 几种用法的异同,这次的...

    Ruby中使用Block、Proc、lambda实现闭包

    Ruby中的闭包实现有:Block,Proc,Lambada。 首先,我们来看Block。 代码如下: ary = [1,2,3,4] ary.collect! do |a|  a*a end ary.each do |a|  puts a end 这段代码,我们使用了Array对象的block方法,将ary中...

    procfs:procfs提供了从伪文件系统proc检索系统,内核和进程指标的功能

    某些子软件包(例如blockdevice )需要访问proc和sys文件系统。 fs , err := blockdevice . NewFS ( "/proc" , "/sys" ) stats , err := fs . ProcDiskstats () 包装组织 该项目中的软件包是根据(1)数据

    multi_block:将多个块传递给 Ruby 方法

    多块 MultiBlock 是一个迷你框架,用于将多个块传递给方法。 它使用以简单的语法完成此操作。 接收方法可以产生所有块...yield :success # calls :success proc without args yield :success , "Code Brawl!" # calls

    Linux读取U盘或者移动硬盘序列号并获取U盘或者移动硬盘分区名

    这个数字与前面 /proc/scsi/usb-storage目录中的相对应,子目录表示sata硬盘。比如 /sys/class/scsi_device/2:0:0:0/device/block 中有USB设备,从该目录下得到U盘或者移动硬盘的分区名,比如sda1。 该demo实现了...

    详解Ruby中的代码块对象Proc

    在Ruby中一个代码块block不是对象,但可以用Proc来替代其作为对象进行操作,接下来我们就来详解Ruby中的代码块对象Proc

    Ruby中的block代码块学习教程

    在Ruby中,block并不是类,block可以被转化为Proc类中衍生出的对象,刚接触Ruby的话block是很难理解的一个点,接下来就为大家来总结Ruby中的block代码块学习教程

    编译上机-自上而下的语法分析

    编译上机-自上而下的语法分析

    matlab开发-JEPEGCODEC

    matlab开发-JEPEGCODEC。jpeg编码器和解码器,不使用block proc函数。

    ORANGES'_自己动手写操作系统_光盘源代码.zip

    EXTERN struct super_block super_block[NR_SUPER_BLOCK]; extern u8 * fsbuf; extern const int FSBUF_SIZE; EXTERN MESSAGE fs_msg; EXTERN struct proc * pcaller; EXTERN struct inode * root_inode; ...

    squashfs2.2-r2.tar.gz

    -b <block_size> set data block to <block_size>. Default 65536 bytes -2.0 create a 2.0 filesystem -noI do not compress inode table -noD do not compress data blocks -noF do not compress ...

    The Little SAS Book(Fourth)

    creating new variables in PROC REPORT with a COMPUTE block WHERE= data set option SORTSEQ=LINGUISTIC option in PROC SORT more functions, including ANYALPHA, CAT, PROPCASE, and YRDIF About the ...

    Linux那些事儿 之 我是Sysfs上.pdf

    去/sys看一看, localhost:/sys#ls /sys/ block/ bus/ class/ devices/ firmware/ kernel/ module/ power/ Block目录:包含所有的块设备 Devices目录:包含系统所有的设备,并根据设备挂接的总线类型组织成层次结构 ...

    Linux那些事儿 之 我是Sysfs下.pdf

    去/sys看一看, localhost:/sys#ls /sys/ block/ bus/ class/ devices/ firmware/ kernel/ module/ power/ Block目录:包含所有的块设备 Devices目录:包含系统所有的设备,并根据设备挂接的总线类型组织成层次结构 ...

    meddleware_rb:一个中间件框架,使干预变得容易

    Meddleware 一个使干预变得容易的中间件框架。 require 'meddleware' middleware = Meddlware .... use Tracer after Tracer , Logger... middleware -类,实例或Proc。 必须实现.call 。 block可选块,可以传递给中间

    squashfs1.3r3.tar.gz

    block device/memory systems (e.g. embedded systems) where low overhead is needed. The section 'mksquashfs' gives information on using the mksquashfs tool to create and append to squashfs filesystems....

    IO流程解析与基本原理

    希望对学习块设备的同学有帮助了通过/proc/devices 能够看到这个块设备驱动注册了. kobject_add在sys/block/下面建立文件

    dcpcrypt_decrpt_TDCP_TheProcedure_

    procedure TDCP_blockcipher.Init - Use this proc to initialize the cipher withthe key data. Size is the size of the key data you are supplying in BITS.IVector is a pointer to the initialization vector ...

    cyber_kustom_component:该框架旨在帮助开发接口,为组件提供易于编辑的特征

    使用Cyber​​KustomComponent库,您可以快速编辑组件的主要视觉特征。 要将新组件添加到netbeans面板,请。 可以通过下载Jar 版本0.1.0具有以下组件: -KTextField == JTextField; -KPasswordField == ...

Global site tag (gtag.js) - Google Analytics