list(object) 类型的表达式不符合预期的列表 scala

0 scala list append object cumulative-sum

据说我有以下内容

case class test {
                   a:string
                   b: string
                   c: Int
                   d: Int }


var temp = List(test("lol","lel",1,2))
var total = List(test)

total = total:::temp //this doesn't work because temp is of type [test] while total is of type [test.type]
Run Code Online (Sandbox Code Playgroud)

我不明白其中的区别。我想使用它的原因是我想要一个运行列表,其中元素将有条件地添加到循环中。所以在这种情况下,total最初应该是一个接受test对象的空列表。我该怎么做呢?

任何反馈表示赞赏!

Sar*_*ngh 6

让我首先解释一些关于 Scala 的基础知识。

在 Scala 中,您定义一个类,如下所示,

scala> class Demo(a: String, b: Int) {
 |   def stringify: String = a + " :: " + b
 | }
// defined class Demo
Run Code Online (Sandbox Code Playgroud)

您可以将 aclass视为提供给 Scala 的蓝图,它将用于创建 that 的实例class。在这里, 的每个实例class Demo都有两个属性——a它们是 a Stringb哪个是 anInt和一个方法——stringify它们将返回 a String

scala> val demo1 = new Demo("demo1", 1)
// demo1: Demo = Demo@21eee94f

scala> demo1.getClass
// res0: Class[_ <: Demo] = class Demo
Run Code Online (Sandbox Code Playgroud)

demo1class Demo和 has 的一个实例type Demo

Scala 也有一个概念,object即专门生成的内部类的实例。

scala> object OtherDemo {
 | val a: Int = 10
 | }
// defined object OtherDemo

scala> DemoObject.getClass
// res2: Class[_ <: OtherDemo.type] = class OtherDemo$
Run Code Online (Sandbox Code Playgroud)

这里OtherDemo将是那个特别生成的唯一实例,class OtherDemo$并且具有type OtherDemo.type.

然后case class在 Scala 中有

scala> case class AnotherDemo(a: Int)
// defined class AnotherDemo
Run Code Online (Sandbox Code Playgroud)

这不仅会创建一个,class AnotherDemo而且还会创建一个object AnotherDemo我们称之为伴随对象的对象。这相当于,

class AnotherDemo(a: Int)

object AnotherDemo {

  def apply(a: Int): AnotherDemo = new AnotherDemo(a)

  def unapply(anotherDemo: AnotherDemo): Option[Int] = Some(anotherDemo.a)

  // And many more utility functions
}
Run Code Online (Sandbox Code Playgroud)

我们把这个object AnotherDemo作为companion objectclass AnotherDemo

我们可以通过AnotherDemo两种方式创建实例,

// By using new keyword, as we can do for any class
scala> val anotherDemo1 = new AnotherDemo(1)
// anotherDemo1: AnotherDemo = AnotherDemo(1)

// Or we can use `apply` method provided by companion object
scala> val anotherDemo2 = AnotherDemo(2)
// anotherDemo2: AnotherDemo = AnotherDemo(2)

scala> anotherDemo1.getClass
// res6: Class[_ <: AnotherDemo] = class AnotherDemo

scala> anotherDemo2.getClass
// res7: Class[_ <: AnotherDemo] = class AnotherDemo

scala> AnotherDemo.getClass
// res8: Class[_ <: AnotherDemo.type] = class AnotherDemo$
Run Code Online (Sandbox Code Playgroud)

此外,在 Scala 中,您的类名应以大写字母开头。这使您可以轻松地将它们与应以小写字母开头的实例变量区分开来。这有助于您避免混淆。

现在,它应该是a: String而不是a: string

scala> case class Test(
 |       a: String,
 |       b: String,
 |       c: Int,
 |       d: Int
 |     )
// defined class Test
Run Code Online (Sandbox Code Playgroud)

现在,当你写作时,

scala> var temp = List(Test("lol","lel",1,2))
// temp: List[Test] = List(Test(lol,lel,1,2))
Run Code Online (Sandbox Code Playgroud)

它实际上相当于,

var temp = List.apply(Test.apply("lol","lel",1,2))
Run Code Online (Sandbox Code Playgroud)

或者,

val test1 = Test.apply("lol","lel",1,2)
var temp = List.apply(test1)
Run Code Online (Sandbox Code Playgroud)

TestTest.apply是不是你的class Test,但companion object Test。并调用Test.apply返回的实例class Test ,其被传递到List.apply最终得到Listtype List[Test]含有这种情况Test

但是当你写这个的时候

scala> var total = List(Test)
// total: List[Test.type] = List(Test)
Run Code Online (Sandbox Code Playgroud)

您正在创建一个ListList[Test.type]包含companion objectTest

专注于total: List[Test.type]一部分......这意味着,totalvariabletype List[Test.type],这意味着它会想点到value/instancetype List[Test.type],并拒绝点别的。

现在......你正在尝试这样做,

total = total ::: temp
Run Code Online (Sandbox Code Playgroud)

这相当于,

val x = total ::: temp
total = x
Run Code Online (Sandbox Code Playgroud)

实际上,

val x = temp.:::(total)
total = x
Run Code Online (Sandbox Code Playgroud)

现在看看这个val x = total ::: temp

scala> val x = total ::: temp
// x: List[Serializable] = List(Test, Test(lol,lel,1,2))
Run Code Online (Sandbox Code Playgroud)

你看……这x是类型List[Serializable]。所以当你尝试时total = x,你会得到以下错误,

scala> total = x
// <console>:13: error: type mismatch;
// found   : List[Serializable]
// required: List[Test.type]
//       total = x
//               ^
Run Code Online (Sandbox Code Playgroud)

这意味着total需要 aList[Test.type]但你给它一个List[Serializable].

  • 这个论坛并不是要让答案“尽可能短”。更重要的是确保您回答问题并帮助社区。 (3认同)