groovy邮件功能_Groovy中的功能部件,第3部分

编程语言可以为您处理的细节越低,让您引入错误和复杂性的地方就越少。 (经典示例是JVM上的垃圾收集和内存管理。)正如我在前几期中所强调的那样,功能语言和具有功能功能的动态语言的特征之一是,它们使您可以选择性地放弃对平​​凡的控制。语言和运行时的详细信息。 例如,在“ Groovy的功能特性,第1部分 ”中,我展示了递归如何消除了开发人员维护状态的需要。 在本期中,我对使用Groovy进行缓存也做同样的事情。

缓存是一个常见的要求(也是难以发现的错误的来源)。 在面向对象的语言中,缓存通常发生在数据对象级别,并且开发人员必须自己进行管理。 许多函数式编程语言通过称为备忘录的机制在函数级别构建缓存。 在本文中,我研究了函数的两个缓存用例:类内调用与外部调用。 我还说明了实现缓存的两种替代方法:手工制作的状态和备注。

方法级缓存

如果您已经阅读了本系列的任何一期文章,那么您就会熟悉数字分类的问题(在第一期中有解释)。 本文的起点是Groovy版本(在上一期中派生),如清单1所示:

清单1. Groovy中的分类器
class Classifier {
  def static isFactor(number, potential) {
    number % potential == 0;
  }

  def static factorsOf(number) {
    (1..number).findAll { i -> isFactor(number, i) }
  }

  def static sumOfFactors(number) {
    factorsOf(number).inject(0, {i, j -> i + j})
  }

  def static isPerfect(number) {
    sumOfFactors(number) == 2 * number
  }

  def static isAbundant(number) {
    sumOfFactors(number) > 2 * number
  }

  def static isDeficient(number) {
    sumOfFactors(number) < 2 * number
  }
}

可以通过使用我在“从功能上思考,第2部分 ”中介绍的技巧来优化清单1中 factorsOf()方法的内部算法,但是对于此示例,我对函数级缓存更感兴趣。

由于Classifier类对数字进行分类,因此其通用用法是通过多种方法对同一数字进行分类。 例如,考虑清单2中的代码:

清单2.数字分类的常用用法
//...
if (Classifier.isPerfect(n)) print '!'
else if (Classifier.isAbundant(n)) print '+'
else if (Classifier.isDeficient(n)) print '-'
//...

在当前的实现中,我必须为我调用的每个分类方法重新计算因子之和。 这是类内缓存的一个示例:在正常使用期间,通常每个数字多次调用sumOfFactors()方法。 在这种常见的用例中,这是一种低效的方法。

缓存总和

使代码更高效的方法之一是利用已经完成的艰苦工作。 因为生成因子之和的成本很高,所以我只希望对每个数字执行一次。 为此,我创建了一个用于存储计算的缓存,如清单3所示:

清单3.缓存总和
class ClassifierCachedSum {
  private sumCache

  ClassifierCachedSum() {
    sumCache = [:]
  }

  def su
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值