Scala Language
Le tuple
Ricerca…
Osservazioni
Perché le tuple sono limitate alla lunghezza 23?
Le tuple vengono riscritte come oggetti dal compilatore. Il compilatore ha accesso a Tuple1
attraverso Tuple22
. Questo limite arbitrario è stato deciso dai progettisti di linguaggi.
Perché le lunghezze di tuple contano da 0?
Una Tuple0
è equivalente a Unit
.
Creazione di una nuova tupla
Una tupla è una raccolta eterogenea di valori compresi tra due e ventidue. Una tupla può essere definita usando le parentesi. Per le tuple di dimensione 2
(anche chiamata 'coppia') c'è una sintassi delle frecce.
scala> val x = (1, "hello") x: (Int, String) = (1,hello) scala> val y = 2 -> "world" y: (Int, String) = (2,world) scala> val z = 3 → "foo" //example of using U+2192 RIGHTWARD ARROW z: (Int, String) = (3,foo)
x
è una tupla di dimensione due. Per accedere agli elementi di una tupla usare ._1
, attraverso ._22
. Ad esempio, possiamo usare x._1
per accedere al primo elemento della tupla x
. x._2
accede al secondo elemento. Più elegantemente, puoi usare gli estrattori di tuple .
La sintassi della freccia per la creazione di tuple di dimensione due viene principalmente utilizzata in Maps, che sono raccolte di coppie (key -> value)
:
scala> val m = Map[Int, String](2 -> "world") m: scala.collection.immutable.Map[Int,String] = Map(2 -> world) scala> m + x res0: scala.collection.immutable.Map[Int,String] = Map(2 -> world, 1 -> hello) scala> (m + x).toList res1: List[(Int, String)] = List((2,world), (1,hello))
La sintassi per la coppia nella mappa è la sintassi della freccia, rendendo chiaro che 1 è la chiave e a è il valore associato a quella chiave.
Tuple all'interno delle collezioni
Le tuple sono spesso utilizzate all'interno delle raccolte ma devono essere gestite in un modo specifico. Ad esempio, dato il seguente elenco di tuple:
scala> val l = List(1 -> 2, 2 -> 3, 3 -> 4)
l: List[(Int, Int)] = List((1,2), (2,3), (3,4))
Può sembrare naturale aggiungere gli elementi insieme usando la tupla-disimballaggio implicita:
scala> l.map((e1: Int, e2: Int) => e1 + e2)
Tuttavia, ciò comporta il seguente errore:
<console>:9: error: type mismatch;
found : (Int, Int) => Int
required: ((Int, Int)) => ?
l.map((e1: Int, e2: Int) => e1 + e2)
Scala non può decomprimere implicitamente le tuple in questo modo. Abbiamo due opzioni per correggere questa mappa. Il primo è usare gli accessori posizionali _1
e _2
:
scala> l.map(e => e._1 + e._2)
res1: List[Int] = List(3, 5, 7)
L'altra opzione è usare un'istruzione case
per decomprimere le tuple usando la corrispondenza del modello:
scala> l.map{ case (e1: Int, e2: Int) => e1 + e2}
res2: List[Int] = List(3, 5, 7)
Queste restrizioni si applicano a qualsiasi funzione di ordine superiore applicata a una raccolta di tuple.