科技行者

行者学院 转型私董会 科技行者专题报道 网红大战科技行者

知识库

知识库 安全导航

至顶网软件频道跨越边界: 活动记录和 Java 编程中特定于域的语言

跨越边界: 活动记录和 Java 编程中特定于域的语言

  • 扫一扫
    分享文章到微信

  • 扫一扫
    关注官方公众号
    至顶头条

在这篇文章中,将学习 Ruby 提供的一些漂亮方式,可以集成干净的 DSL,让您大开眼界,用一种新的参考框架来审视 Java 的选项。

作者:baggio785 来源:CSDN 2008年2月29日

关键字: java 活动记录

  • 评论
  • 分享微博
  • 分享邮件

在本页阅读全文(共5页)

可选的扩展

活动记录充分利用了 Ruby 的另一个特性。会经常看到带有可选参数的 Ruby 方法,可选参数是一个默认为空的哈希 map。可以用这种方式模拟命名参数。例如,活动记录方法 belongs_to 的定义看起来像这样:


def belongs_to(association_id, options = {})

现在可以把选项传递给 belongs_to 来优化它的行为:


class Manager < ActiveRecord::Base
 has_one :department, :foreign_key => "department_number"
end

在 Ruby 中,用 key => value 指定哈希 map 的条目。意思很清楚:想让活动记录覆盖默认值(department_id,根据命名规范)而采用 department_number。因为可以修剪选项的名称来满足语法的要求,所以 DSL 就得到了另一个强大的特性:可选的扩展。下面需要的能力是用自己的词汇来扩展 Ruby 语言。

修饰现有类型

Ruby 是种动态语言,所以向现有类(甚至指定类的实例)添加行为很容易。现在先使用这项技术来针对某个域修饰现有类,然后再根据词汇扩展现有类。

罗马数字的使用不太频繁,但是在某些上下文中会有用。我们并不想直接把罗马数字添加到 Ruby 的 Fixnum 基类,但是它们对于特定于域的语言可能是有用的。可以把 to_roman 方法添加到 Fixnum 类,这个方法把 fixnum 转换成罗马数字。这件事做起来极为容易。只要再次打开类定义,并定义新方法即可。清单 3 显示了一个粗糙的罗马数字处理方法:


清单 3. 罗马数字处理方法


class Fixnum
 def to_roman
  value = self
  str = ""
  (str << "C"; value = value - 100) while (value >= 100)
  (str << "XC"; value = value - 90) while (value >= 90)
  (str << "L"; value = value - 50) while (value >= 50)
  (str << "XL"; value = value - 40) while (value >= 40)
  (str << "X"; value = value - 10) while (value >= 10)
  (str << "IX"; value = value - 9) while (value >= 9)
  (str << "V"; value = value - 5) while (value >= 5)
  (str << "IV"; value = value - 4) while (value >= 4)
  (str << "I"; value = value - 1) while (value >= 1)
  str
 end
end

一旦理解了分号分隔了两个不同的 Ruby 语句,清单 3 就简单了。当我想让两个不同的想法挂在一起的时候,就经常用这种方式。可以用这项技术添加或修改任何 Ruby 类的定义。这一特殊实现的好处在于使用模型。可以把它粘贴到一个文件中,并在 Ruby 解释器中使用它,如清单 4 所示:

清单 4. 使用 to_roman 扩展


irb(main):001:0> load 'to_roman.rb'
=> true
irb(main):002:0> 10.to_roman
=> "X"
irb(main):003:0> 199.to_roman
=> "CXCIX"
irb(main):004:0>

Rails 利用这个能力处理像时间测量之类的事情。例如,在 Rails 应用程序中,可以说 10.days ,或 2.hours.ago,或 5.minutes.from_now。使用这个技术,可以把现有 Ruby 词汇扩展到自己的域中,处理类似测量、转换或其他语法组合的事情。最终结果是一个干净漂亮的 Ruby 核心类,带有一些扩展,提供特定于域的类,可以在域的上下文中做正确的事。

    • 评论
    • 分享微博
    • 分享邮件
    邮件订阅

    如果您非常迫切的想了解IT领域最新产品与技术信息,那么订阅至顶网技术邮件将是您的最佳途径之一。

    重磅专题
    往期文章
    最新文章