Skip to content

Instantly share code, notes, and snippets.

@scarf005
Created April 4, 2025 01:13
Show Gist options
  • Save scarf005/ae3881ec5d47b9fb102e029f6542e570 to your computer and use it in GitHub Desktop.
Save scarf005/ae3881ec5d47b9fb102e029f6542e570 to your computer and use it in GitHub Desktop.
import scala.annotation.tailrec
sealed abstract class SnocList[+A]:
inline def :<[B >: A](a: B): SnocList[B] = new :<(this, a)
final def toList: List[A] =
@tailrec def go(xs: SnocList[A], acc: List[A]): List[A] = xs match
case Lin => acc
case xs :< x => go(xs, x :: acc)
go(this, Nil)
override def toString: String = toList.mkString("SnocList(", ", ", ")")
final case class :<[+A](init: SnocList[A], last: A) extends SnocList[A]
case object Lin extends SnocList[Nothing]
object SnocList:
def apply[A](as: A*): SnocList[A] =
@tailrec def go(as: List[A], acc: SnocList[A]): SnocList[A] = as match
case Nil => acc
case x :: xs => go(xs, acc :< x)
go(as.toList, Lin)
extension [A](xs: IterableOnce[A])
def toSnocList: SnocList[A] = SnocList(xs.iterator.toSeq*)
val xs = Lin :< 1 :< 2 :< 3
val ys = xs match
case Lin => println("Empty")
case xs :< x => println(s"Snoc($xs, $x)")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment