scala val 与var 区别
来源:互联网 发布:网络版收银软件 编辑:程序博客网 时间:2024/05/16 09:32
一个var和VAL定义在Scala之间的区别是什么?
一之间的区别是什么var
和val
在Scala中定义和为什么的语言都需要?为什么你会选择val
在一个var
反之亦然?
1. 正如许multiplayer所说,该对象分配给一个val
不能被替换,并且该对象分配给一个var
可以。然而,该对象可以有其内部状态改变。例如:class A(n: Int) { var value = n}class B(n: Int) { val value = new A(n)}object Test { def main(args: Array[String]) { val x = new B(5) x = new B(6) // Doesn't work, because I can't replace the object created on the line above with this new one. x.value = new A(6) // Doesn't work, because I can't replace the object assigned to B.value for a new one. x.value.value = 6 // Works, because A.value can receive a new object. }}
所以,尽管我们不能改变分配给对象x
,我们可以改变对象的状态。在它的根,然而 CodeGo.net,有一个var
。 现在,是不可改变的原因有很多好东西。首先,如果一个对象不改变内部状态,你不必担心,如果你的代码的其他部分改变它。例如:x = new B(0)f(x)if (x.value.value == 0) println("f didn't do anything to x")else println("f did something to x")
这与多线程系统尤为重要。在多线程系统中,会出现以下情况:x = new B(1)f(x)if (x.value.value == 1) { print(x.value.value) // Can be different than 1!}
如果val
和不可变的数据结构(即,避免数组,一切都在scala.collection.mutable
等),你可以放心不会出现这种情况。也就是说,除非有代码,甚至一做反思技巧-反射可以改变“一成不变”的价值观,很遗憾。 这是原因之一,但还有另外一个原因吧。何时var
,你可以引诱到var
用于多种用途。这有问题: 这将是更困难的人阅读代码知道什么是可变的代码中的某一部分的值。 您可能忘记重新初始化代码路径变量,并最终在代码下游传递错误的价值观。 简单地说,使用val
更安全,并导致更易读的代码。 我们可以的话,去了另一个方向。如果val
是更好的,为什么var
呢?那么,语言没有采取这条路线,但也有在哪些情况下可变性提高性能,很多。 例如,考虑一个不可变的Queue
。当你要么enqueue
或dequeue
在它的东西,你得到一个新的Queue
对象。怎么样的话,你会去处理它的所有项目? 我会去通过一个例子。比方说,你有数字的队列,你想了许多了出来。举例来说,如果我有一个队列,2,1,3,按照这个顺序,我想拿回数213。让我们先解决它与mutable.Queue
:def toNum(q: scala.collection.mutable.Queue[Int]) = { var num = 0 while (!q.isEmpty) { num *= 10 num += q.dequeue } num}
此代码是快速和容易理解。它的主要缺点是,所传递的队列由modifiedtoNum
,所以你必须做出一个副本事前。这就是一种对象的immutability是你通过free的。 现在,让我们隐蔽它的immutable.Queue
:def toNum(q: scala.collection.immutable.Queue[Int]) = { def recurse(qr: scala.collection.immutable.Queue[Int], num: Int): Int = { if (qr.isEmpty) num else { val (digit, newQ) = qr.dequeue recurse(newQ, num * 10 + digit) } } recurse(q, 0)}
我不变量来轨迹我num
,就像在这个例子中,我需要求助于递归。在这种情况下,它是一个尾递归,其中有相当不错的表现。但事实并非总是如此:他们就是没有好(可读,简单)尾递归的解决方案。 但是,请注意,我可以重写这些代码的immutable.Queue
和var
在例如:def toNum(q: scala.collection.immutable.Queue[Int]) = { var qr = q var num = 0 while (!qr.isEmpty) { val (digit, newQ) = qr.dequeue num *= 10 num += digit qr = newQ } num}
此代码仍然是有效的,不需要递归,你不必担心你是否有让你的队列与否的一个副本之前调用toNum
。当然,我避免用于其他用途的变量,而这个函数之外没有代码能够看到他们,所以我并不需要担心他们的价值观改变从一行到下一个-除非我明确地这样做。 Scala的选择,让这样做,如果它是最好的解决方案。其他语言的选择做出这样的代码很难。价格scala(和广泛的可变性的任何语言)支付是不拥有尽可能多的回旋余地在优化代码,因为它可能并非如此。 Java的答案是优化的基础上运行配置文件的代码。我们会继续和有关利弊两侧。 就个人而言,我认为Scala的罢工适当的平衡,现在。它不是完美的,到目前为止。我认为无论是Clojure和Haskell中没有采纳scala非常有趣的概念,但Scala有其自身的优势,以及。我们将看到了未来。
2. val
在决赛中,也就是说,不能设置。想final
在java中。
3. 不同的是,一个var
可以被重新分配给一个而val
不能。的可变性,或其他任何实际分配,是一个次要的问题:import collection.immutableimport collection.mutablevar m = immutable.Set("London", "Paris")m = immutable.Set("New York") //Reassignment - I have change the "value" at m.
鉴于:val n = immutable.Set("London", "Paris")n = immutable.Set("New York") //Will not compile as n is a val.
因此:val n = mutable.Set("London", "Paris")n = mutable.Set("New York") //Will not compile, even though the type of n is mutable.
如果你正在建设一个数据结构,它的所有字段都val
s,则该数据结构是不变的,因此,它的状态不能改变。
4. val
表示不可变的,var
指可变的。 满
5. “不变的,可变的。” 意译,“价值与变量”。 出现这种情况是重要的(这两个概念的定义是什么程序是所有的本质),以及面向对象已经成功在面向对象的blur区分,唯一的公理是:“一切都是对象”。并且,作为一个结果,大量的这些日子往往不理解/欣赏/承认,他们已经被洗脑成“思想的面向对象的方式”往往导致可变/可变对象一样无处不在,当值/不可变的对象可能/经常有好些。
class A(n: Int) { var value = n}class B(n: Int) { val value = new A(n)}object Test { def main(args: Array[String]) { val x = new B(5) x = new B(6) // Doesn't work, because I can't replace the object created on the line above with this new one. x.value = new A(6) // Doesn't work, because I can't replace the object assigned to B.value for a new one. x.value.value = 6 // Works, because A.value can receive a new object. }}
x = new B(0)f(x)if (x.value.value == 0) println("f didn't do anything to x")else println("f did something to x")
x = new B(1)f(x)if (x.value.value == 1) { print(x.value.value) // Can be different than 1!}
def toNum(q: scala.collection.mutable.Queue[Int]) = { var num = 0 while (!q.isEmpty) { num *= 10 num += q.dequeue } num}
def toNum(q: scala.collection.immutable.Queue[Int]) = { def recurse(qr: scala.collection.immutable.Queue[Int], num: Int): Int = { if (qr.isEmpty) num else { val (digit, newQ) = qr.dequeue recurse(newQ, num * 10 + digit) } } recurse(q, 0)}
def toNum(q: scala.collection.immutable.Queue[Int]) = { var qr = q var num = 0 while (!qr.isEmpty) { val (digit, newQ) = qr.dequeue num *= 10 num += digit qr = newQ } num}
import collection.immutableimport collection.mutablevar m = immutable.Set("London", "Paris")m = immutable.Set("New York") //Reassignment - I have change the "value" at m.
val n = immutable.Set("London", "Paris")n = immutable.Set("New York") //Will not compile as n is a val.
val n = mutable.Set("London", "Paris")n = mutable.Set("New York") //Will not compile, even though the type of n is mutable.
0 0
- scala val 与var 区别
- scala中的var 与 val
- Scala 的 val与var
- Scala变量定义val与var的区别
- Scala中val和var的区别
- scala val 和 var的区别
- Scala 中 var 和 val 的区别
- 简谈scala 中的val 与 var
- Scala 中的val 与 var 的区别 immutable 与 mutable 的 区别
- Scala var && val
- Scala的var,val
- scala学习笔记-val和var的区别
- 2017.10.16 Scala中val和var的区别
- Scala var val mutable immutable
- Scala中的var val/def
- scala val和var变量
- Scala中的var val/def
- scala中的val 和 var
- python 所有第三方库的一个地址
- 在Greenplum外部表中使用HDFS
- android 建立长连接的方法
- Red Hat linux 6.5 学习使用笔记《二》文件系统及命令详解
- 网站统计中的数据收集原理及实现-埋点统计
- scala val 与var 区别
- 修改网卡IP
- RocketMQ源码调试环境搭建
- bootstrap之双日历时间段选择控件—daterangepicker(汉化版)
- linux c elf文件格式操作之sstrip源码(支持cygwin编译)
- 使用Vysor专业版
- C++中的this指针
- 数组大折腾
- java学习例题之IO流的字节数组复制文件