《Ruby 元编程》读后总结

什么时候需要读这本书?

扫过一遍基本的 Ruby 语法,自己也写过一些 Ruby 代码,觉得 Ruby 也就是一个普通的脚本语言而已的时候。

这本书带给读者什么东西?

在 Ruby 语法背后, Ruby 语言的构建模型。以及在这种模型下,一些可能只属于 Ruby 的实际编程案例(也就是怎么样用 Ruby 的特性去简化和优美你的代码)

那么,元编程是什么?

一般来说,『元xx』这样的词语都表示『创造 xx 的一种东西』或者『xx 背后更加原始的一样类似的东西』,比如 iOS 开发都很熟悉的 OC 中的元类。元编程表示的是『写出可以编写代码的代码』。

还是抽象?举一个小例子:一个类中有二十个属性,现在你需要为这些属性分别创造对应的 set 方法,类似 setXXX 这样的形式,同时要求这些 set 方法都要判断新旧值是否一致,如果一致就直接 return。

这样的事情显然是一个体力活,如果没有好的方法,你就需要写二十个十分类似的方法,并且每个方法内部都差不多,只是在属性的名称那一部分有所区别,重复度非常高。

如果使用 Ruby 的元编程,当外部调用某个 set 方法(比如 setYYY)的时候,你的一段代码就会被执行,这段代码会动态的为当前的类创建一个 setYYY 方法,同时代码中可以截断方法名称(也就是拿到了一个 'YYY' 字符串),通过这个名称去动态获取对应属性的值(一种类似 this.get_property_by_name('YYY') 的方式),和当前 set 方法的参数进行比较,完成 set 方法的要求。整个代码可能不超过十行,并且不重复,十分优雅。

应该怎样阅读这本书?

首先我们来看看这本书每一章的大致内容:

  1. 第一章:简单介绍了 Ruby 中面向对象的模型是怎么实现的,同时讲解了当调用一个对象的方法的时候发生了什么事情。
  2. 第二章:当我们知道方法调用是怎样的一个流程以后,我们就可以考虑是否可以拦截或者修改这个过程来实现一些黑魔法。
  3. 第三章:这里话头一转,转向描述 Ruby 中的代码块,也描述了和代码块息息相关的作用域的概念。
  4. 第四章:这一章把话头又转回了类,这里将详细描述对象与类的组织模型,同时讲解了一些和类有关的元编程方法。
  5. 第五章:着重讲解 eval ,一个能够把字符串当做 Ruby 代码解释的函数。
  6. 第六章:休息一下,用一页纸讲个故事。
  7. 第七章-第八章:通过讲解 ActiveRecord 这个强大库的使用方法,将之前讲过的魔法汇总一下。
  8. 第九章:指出一些使用元编程的注意事项、经验教训。
  9. 附录:给出了一些 Ruby 中的常见事物的惯常写法,解释了什么是 DSL(领域专属语言),然后将前面讲到的魔法的例子汇总了一下。

可以看出,全书主要分两部分,第一部分主要是 Ruby 背后的模型的讲解、高级语法特性的讲解,中间穿插着一些例子。第二部分则是通过解析 ActiveRecord 这个库,将前面讲到的模型的利用来了个实际展示。

因此,最好第一遍阅读的时候着重去理解 Ruby 语言背后的模型,第二遍先看例子,自己尝试想想要实现这些例子通过这些模型还需要什么东西,然后再看实际的例子。最后的附录可以在日后忘记一些写法的时候翻一翻,帮助回忆。

这本书中印象深刻的点?

对象与类的模型和方法调用:

  1. Ruby 中的 class 关键字和 Java 等语言的 class 在理解上很不同,Java 的 class 的作用是在全局创建一个类,并且这个类在全局只能有这一个声明;Ruby 中 class 作用是把代码的上下文变换到这个类中,也就是『打开类』,同一个类可以在任何地方被打开,也因此别人的类可以被自己随意打开并改写。
  2. Ruby 中的实例变量也不像 OC 或者 Java 那样必须提前声明,当第一次用到实例变量的时候,这个实例变量才会生成。所以在方法里头看到对一个实例变量赋值的时候有可能是在初始化这个实例变量。
  3. 对象中不存储方法,只存储属性。对一个对象调用方法的时候,会首先去这个对象的 singlenton class 中找,然后去 singleton class 的父类中(实例对象的 singleton class 的父类是这个实例对象的类,类的 singleton class 的父类是这个类的父类的 singleton class ,类也是对象,不过特殊在类这个对象只有一个)。当调用方法的时候,首先去这个对象的 singleton class 中查找,没有的话继续向 singleton class 的父类查找,在如下完整的对象与类的结构图中可以简单记成『向右一步,然后向上』。
    enter image description here
  4. 定义类方法其实就是向类的 singleton class 中添加新的方法。
  5. 除了使用点语法调用方法,还可以使用 send 方法来调用方法,这样就可以使用字符串拼出来的方法名来调用方法了。(通过 send 甚至可以在外部调用类的私有方法)
  6. 可以使用 define_method 来创建方法,和 def 的区别在于,define_method 后面可以是一个变量。
  7. method_missing 这个方法也可以动态增加方法。注意用这种方式的时候也要重写 respond_to? 方法。
  8. 模块有一个 included 的类方法,在这个模块被 include 的调用,我们可以在里头写上自动增加类方法的代码,这样一个模块被 include 了以后,不止增加了实例方法,还增加了类方法,这个叫做类扩展混入(Class Extension Mixin)
  9. 同样一个 @a ,声明在类的作用域中和类的方法的作用域中是不一样的。前者是类对象的实例变量,后者的类的实例对象的实例变量。

Block: 与 作用域

  1. 任何方法都可以传入一个 block ,不过有的方法会不处理 block ,此时传入 block 什么用也没有。
  2. 一个作用域可以理解为一个上下文环境,在同一个作用域中的代码可以互相访问彼此的变量。当有 class/def/module 的时候,代码会进入一个新的作用域,并且作用域之间并没有什么关系,也就是说内部作用域不会得到外部作用域的变量(除了全局变量,全局变量是可以在任何作用域中得到的)。
  3. 可以使用 block 利用闭包在不同作用域之间传递变量。
  4. block 都是待着作用域的,也就是说 block 这个『行为』带着这个行为创建时的『数据』。
  5. 通过 method(:method_name) 可以得到一个 method 对象,不过 method 对象必须绑定到一个对象上才能被调用。
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,491评论 5 459
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 81,856评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 141,745评论 0 319
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,196评论 1 263
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,073评论 4 355
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,112评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,531评论 3 381
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,215评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,485评论 1 290
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,578评论 2 309
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,356评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,215评论 3 312
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,583评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,898评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,174评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,497评论 2 341
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,697评论 2 335

推荐阅读更多精彩内容

  • 1. Java基础部分 基础部分的顺序:基本语法,类相关的语法,内部类的语法,继承相关的语法,异常的语法,线程的语...
    子非鱼_t_阅读 31,502评论 18 399
  • 从三月份找实习到现在,面了一些公司,挂了不少,但最终还是拿到小米、百度、阿里、京东、新浪、CVTE、乐视家的研发岗...
    时芥蓝阅读 42,137评论 11 349
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,497评论 18 139
  • 最近在追电视剧《军师联盟》,这部剧里边我最喜欢的一个人物就是荀彧。荀彧是东汉末年一位能臣,由于大汉王朝皇帝软弱无能...
    cici爱读书阅读 1,851评论 0 1