Skip to content

Commit

Permalink
Update sbt and shapeless, use project to derive Show for products (#363)
Browse files Browse the repository at this point in the history
  • Loading branch information
joroKr21 authored Jun 7, 2021
1 parent 73d3be4 commit 5b3b7ca
Show file tree
Hide file tree
Showing 3 changed files with 25 additions and 22 deletions.
2 changes: 1 addition & 1 deletion build.sbt
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ val catsVersion = "2.6.1"
val disciplineMunitVersion = "1.0.9"
val kindProjectorVersion = "0.13.0"
val shapeless2Version = "2.3.7"
val shapeless3Version = "3.0.0"
val shapeless3Version = "3.0.1"

lazy val commonSettings = Seq(
scalacOptions := Seq(
Expand Down
43 changes: 23 additions & 20 deletions core/src/main/scala-3/cats/derived/show.scala
Original file line number Diff line number Diff line change
Expand Up @@ -6,25 +6,28 @@ import shapeless3.deriving.{Continue, K0, Labelling}
trait ShowDerivation:

extension (F: Show.type)
inline def derived[A](using gen: K0.Generic[A]): Show[A] = gen.derive(productShow, coproductShow)
inline def derived[A](using gen: K0.Generic[A]): Show[A] =
gen.derive(product, coproduct)

given productShow[A](using inst : => K0.ProductInstances[Show, A], l: Labelling[A]): Show[A] =
(a: A) => {
var idx = 0
val x = inst.foldLeft[StringBuilder](a)(new StringBuilder(s"${l.label}("))(
[t] => (acc: StringBuilder, sh: Show[t], t0: t) => {
//elemLabels is backed by an array so this should be fast
val res = Continue(acc.append(s"${l.elemLabels(idx)}=${sh.show(t0)}, "))
idx = idx + 1
res
}
)
if(idx > 0) {x.delete(x.length - 2, x.length)}
x.append(")")
x.toString()
}
given product[A](using inst: => K0.ProductInstances[Show, A], labelling: Labelling[A]): Show[A] = a =>
val prefix = labelling.label
val labels = labelling.elemLabels
val n = labels.size
if n <= 0 then prefix else
val sb = new StringBuilder(prefix)
sb.append('(')
var i = 0
while i < n do
sb.append(labels(i))
sb.append('=')
sb.append(inst.project(a)(i)([t] => (show: Show[t], x: t) => show.show(x)))
sb.append(", ")
i += 1

given coproductShow[A](using inst: => K0.CoproductInstances[Show, A]): Show[A] =
(a: A) => inst.fold[String](a)(
[t] => (sh: Show[t], t0: t) => sh.show(t0)
)
val l = sb.length
sb.delete(l - 2, l)
sb.append(')')
sb.toString

given coproduct[A](using inst: => K0.CoproductInstances[Show, A]): Show[A] =
inst.fold(_)([t] => (show: Show[t], x: t) => show.show(x))
2 changes: 1 addition & 1 deletion project/build.properties
Original file line number Diff line number Diff line change
@@ -1 +1 @@
sbt.version=1.5.1
sbt.version=1.5.3

0 comments on commit 5b3b7ca

Please sign in to comment.