Scala: Nil - Liste ()


128

Scala'da Nilve arasında herhangi bir fark var List()mı?

Değilse, hangisi daha deyimsel Scala stili? Hem yeni boş listeler oluşturmak hem de boş listelerde desen eşleştirmek için.

Yanıtlar:


188
scala> println (Nil == List())
true

scala> println (Nil eq List())
true

scala> println (Nil equals List())
true

scala> System.identityHashCode(Nil)
374527572

scala> System.identityHashCode(List())
374527572

Nil daha deyimseldir ve çoğu durumda tercih edilebilir. Sorular?


11
Bunun Nildaha deyimsel olduğunu söyleyebilirsin .
Rex Kerr

6
"Eq" nin zaten ne söylediğini açıklığa kavuşturmak için System.identityHashCode eklendi - bunlar aynı nesne.
James Iry

18
Ayrıca Nil bir nesneye doğrudan başvururken List () bir yöntem çağrısıdır.
Jean-Philippe Pellet

6
Is not List[A]()(değil NilfoldLeft için bir akümülatör değeri olarak gerekli)? Örnek - Burada akümülatör olarak scala> Map(1 -> "hello", 2 -> "world").foldLeft(List[String]())( (acc, el) => acc :+ el._2) res1: List[String] = List(hello, world)kullanmak Nilişe yaramaz.
Kevin Meredith

6
Map(1 -> "hello", 2 -> "world").foldLeft(Nil: List[String])( _ :+ _._2)
Raul

85

Kullanıcı bilinmeyen çalışma zamanı hem değeri göstermiştir Nilve List()aynıdır. Ancak statik türleri şu değildir:

scala> val x = List()
x: List[Nothing] = List()

scala> val y = Nil
y: scala.collection.immutable.Nil.type = List()

scala> def cmpTypes[A, B](a: A, b: B)(implicit ev: A =:= B = null) = if (ev eq null) false else true
cmpTypes: [A, B](a: A, b: B)(implicit ev: =:=[A,B])Boolean

scala> cmpTypes(x, y)
res0: Boolean = false

scala> cmpTypes(x, x)
res1: Boolean = true

scala> cmpTypes(y, y)
res2: Boolean = true

Bu, örneğin bir katlamanın toplayıcısında olduğu gibi bir türü çıkarmak için kullanıldığında özellikle önemlidir:

scala> List(1, 2, 3).foldLeft(List[Int]())((x, y) => y :: x)
res6: List[Int] = List(3, 2, 1)

scala> List(1, 2, 3).foldLeft(Nil)((x, y) => y :: x)
<console>:10: error: type mismatch;
 found   : List[Int]
 required: scala.collection.immutable.Nil.type
       List(1, 2, 3).foldLeft(Nil)((x, y) => y :: x)
                                               ^

2 :: Nil'in neden çalıştığını ama
fold'ın

2
@FUD Eh, y :: x yaptığı işi. Sorun, döndürdüğü türün beklenen tür olmamasıdır. List[Int]Beklenen tip ya ya List[Nothing]da Nil.type(sanırım birincisi, ama belki ikincisi) iken geri döner .
Daniel C. Sobral

27

Bilinmeyen kullanıcının cevabının gösterdiği gibi, bunlar aynı nesnedir.

İdiomatik olarak Nil güzel ve kısa olduğu için tercih edilmelidir. Yine de bir istisna var: düşündüğüm herhangi bir nedenle açık bir türe ihtiyaç duyulursa

List[Foo]() 

daha güzel

Nil : List[Foo]

36
List.empty[Foo]Üçüncü bir alternatif olarak da var .
kassens
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.