Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 11 additions & 1 deletion library/src/scala/NamedTuple.scala
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package scala
import compiletime.ops.boolean.*
import collection.immutable.{SeqMap, ListMap}

import language.experimental.captureChecking

Expand Down Expand Up @@ -30,7 +31,7 @@ object NamedTuple:
import NamedTupleDecomposition.{Names, DropNames}
export NamedTupleDecomposition.{
Names, DropNames,
apply, size, init, head, last, tail, take, drop, splitAt, ++, map, reverse, zip, toList, toArray, toIArray
apply, size, init, head, last, tail, take, drop, splitAt, ++, map, reverse, zip, toList, toArray, toIArray, toSeqMap
}

extension [N <: Tuple, V <: Tuple](x: NamedTuple[N, V])
Expand Down Expand Up @@ -209,6 +210,15 @@ object NamedTupleDecomposition:
/** An immutable array consisting of all element values */
inline def toIArray: IArray[Object] = x.toTuple.toIArray

/** An immutable map consisting of all element values preserving the order of fields.
* Keys are the names of the elements.
*/
inline def toSeqMap: SeqMap[String, Tuple.Union[V]] =
inline compiletime.constValueTuple[N].toList match
case names: List[String] =>
ListMap.from(names.iterator.zip(
x.toTuple.productIterator.asInstanceOf[Iterator[Tuple.Union[V]]]
))
end extension

/** The names of a named tuple, represented as a tuple of literal string values. */
Expand Down
9 changes: 6 additions & 3 deletions tests/run/named-tuple-ops.scala
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
//> using options -source future
import scala.compiletime.asMatchable
import scala.collection.immutable.{ListMap, SeqMap}

type City = (name: String, zip: Int, pop: Int)
type Raw = (String, Int, Int)
Expand Down Expand Up @@ -82,7 +83,9 @@ type Labels = (x: String, y: String)
val _: List[String | Int] = cityFields
assert(cityFields == List("Lausanne", 1000, 140000))

val citArr = city.toArray
val _: List[String | Int] = cityFields
assert(cityFields == List("Lausanne", 1000, 140000))
val cityArr = city.toArray
assert(cityArr.sameElements(Array("Lausanne", 1000, 140000)))

val cityMap = city.toSeqMap
val _: SeqMap[String, String | Int] = cityMap
assert(cityMap == ListMap("name" -> "Lausanne", "zip" -> 1000, "pop" -> 140000))
Loading