加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

Scala中关闭的内存管理如何工作?

发布时间:2020-12-16 09:18:04 所属栏目:安全 来源:网络整理
导读:Scala允许关闭 def newCounter = { var a=0 () = {a+=1;a}} 它定义了一个函数,每个调用返回一个新的独立计数器函数,从1开始: scala val counter1 = newCountercounter1: () = Int = function0scala counter1()res0: Int = 1scala counter1()res1: Int = 2sc
Scala允许关闭

def newCounter = {
  var a=0
  () => {a+=1;a}
}

它定义了一个函数,每个调用返回一个新的独立计数器函数,从1开始:

scala> val counter1 = newCounter
counter1: () => Int = <function0>

scala> counter1()
res0: Int = 1

scala> counter1()
res1: Int = 2

scala> val counter2 = newCounter
counter2: () => Int = <function0>

scala> counter2()
res2: Int = 1

scala> counter1()
res3: Int = 3

这是非常令人印象深刻的,因为通常会代表newCounter的堆栈框架上的内存地址.我刚刚阅读了“Scala编程”的封面章节,只有以下几点可以说(第155页):

The Scala compiler rearranges things in cases like this so that the captured parameter lives out on the heap,instead of the stack,and thus can outlive the method call that created it. This rearrangement is all taken care of automatically,so you don’t have to worry about it.

任何人都可以详细说明如何在字节码级别上工作?访问是否类似于具有所有相关同步和性能影响的类的成员变量?

解决方法

您可以使用scalac -Xprint:lambdalift< scala-file-name>调查这个.

你的代码实际上是这样的:

def newCounter = {
  val a: runtime.IntRef = new runtime.IntRef(0);
  new Function0 {
    private[this] val a$1 = a
    def apply() = {
      a$1.elem = a$1.elem + 1
      a$1.elem
    }
  }
}

lambda使用的任何var都有一个包装器.其他var(在闭包中不使用)是常用的区域变量.

到这个包装器的链接在函数的实例中被存储为字段.

-Xprint中的lambdalift:lambdalift是compiler phase.可以使用-Xshow-phase来获取所有阶段.您可以使用阶段编号而不是名称,当您不确定需要哪一阶段时,这很有用.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读