案例对象与对象之间的区别


226

案例对象和scala中的对象之间有什么区别吗?


3
他有一点要说-不必有一个case对象才能在其上进行模式匹配。我认为上一个问题没有解决这个问题……
axel22 2011年

3
我认为模式匹配行为会有所不同,但案例对象和普通对象在模式匹配AFAIK中的行为方式相同。很难找到有关案例对象的任何信息,因此我期待有人启发我们。
年龄Mooij

4
不必使用case具有模式匹配的功能,它只是糖。实施unapply自己就能胜任。
拉斐尔

1
接受的答案只是不回答问题,如对此评论所述。有所作为的为时已晚,但应注意。
itsbruce

编辑接受的答案还为时不晚。编辑将被审查,如果相关,则接受。
C4stor

Answers:


111

案例类与常规类的不同之处在于:

  1. 模式匹配支持
  2. 的默认实现equalshashCode
  3. 序列化的默认实现
  4. 更漂亮的默认实现的toString,并
  5. 他们从自动继承中获得的少量功能scala.Product

模式匹配,等于和hashCode对于单例而言并没有多大关系(除非您真正退化了一些东西),因此您几乎只是获得序列化,一个不错的toString方法,以及一些您可能永远不会使用的方法。


46
答案的第3点和第4点是案例对象与对象之间的正确区别。点1和2对单例对象无关紧要。而且单例对象始终是Arity为0的产品,因此点5也无关紧要。
WojciechDurczyński2011年

86
这个帖子延续了与单身汉object相同的神话。它不是。确切地说,它就是它所说的一个对象,即一个声明和一个实例化。object如果在包范围内定义,则将其限制为单个实例,这实际上使它成为单例,但仅在该范围内定义时才如此。如果在类内部定义,则实例可以与类本身一样多(它是延迟实例化的,因此不一定是1-1)。这些内部对象很可能用作哈希键,这使得默认的equals / hashCode非常明智。
nilskp

66
问题是关于case object不上课,这为什么是正确的答案?
Ixx 2015年

10
这不能回答问题。这个答案与之间的差别交易case classclass。现在的问题是关于之间的差异case objectobject
MK 2015年

6
@ C4stor答案不是那样。对象不是类。鉴于案例类在幕后发挥了不可思议的作用,考虑到Scala的各种边缘案例和复杂性,我们没有理由简单地假设标准Scala对象和案例对象之间的唯一区别是由我们对区别的了解所解释的在标准类和案例类之间。这个答案甚至没有解决问题的措辞。
itbruce

137

这是一个区别-案例对象扩展了Serializable特征,因此可以序列化它们。常规对象默认情况下不能:

scala> object A
defined module A

scala> case object B
defined module B

scala> import java.io._
import java.io._    

scala> val bos = new ByteArrayOutputStream                                            
bos: java.io.ByteArrayOutputStream =  

scala> val oos = new ObjectOutputStream(bos)                                          
oos: java.io.ObjectOutputStream = java.io.ObjectOutputStream@e7da60                   

scala> oos.writeObject(B)

scala> oos.writeObject(A)
java.io.NotSerializableException: A$

15
我认为可以序列化对象的案例与常规对象的区别最大,尤其是在参与者之间的网络通信中
爱国者

14
但是添加extends Serializable应该做同样的技巧。
nilskp

36
scala> object foo

定义对象foo

scala> case object foocase

定义对象foocase

序列化差异:

scala> foo.asInstanceOf[Serializable]

java.lang.ClassCastException:foo $无法转换为scala.Serializable
... 43

scala> foocase.asInstanceOf[Serializable]

res1:可序列化= foocase

toString的区别:

scala> foo

res2:foo.type = foo $ @ 7bf0bac8

scala> foocase

res3:foocase.type = foocase


2

case对象隐含了toString,equals和hashCode方法的实现,而简单对象则没有。case对象可以序列化,而简单对象则不能序列化,这使得case对象作为带有Akka-Remote的消息非常有用。在object关键字之前添加case关键字可以使对象可序列化。


0

这是与同类case classclass,我们只是使用case object的,而不是case class在没有表示附加状态信息的任何领域。


0

我们以前知道对象和“案例类”。但是“案例对象”是两者的混合体,即它是一个与对象相似的单例对象,并且与案例类一样具有很多样板。唯一的区别是样板是为对象而不是类完成的。

case对象将不包含以下对象:

应用,取消应用方法。这里没有复制方法,因为这是一个单例。没有用于结构相等比较的方法。也没有构造函数。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.