Size: a a a

ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)

2020 June 02

λ

λoλdog in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
RattenK 🍄🐀🌹
расширение для гхц
Чёткое определение
источник

λ

λoλdog in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Тоже так буду теперь всегда говорить
источник

GP

Grigory Pomadchin in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
не, 2.12 надо обязательно пока что в тофу поддерживать
Спасибо
источник

R

RattenK 🍄🐀🌹 in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
ок, а как концепт
ну примерно если, то адт на которые натянули генерики(здарова), типа наш адт работает с N неизвестными параметрами и это все разнесено по членам суммы
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
RattenK 🍄🐀🌹
ну примерно если, то адт на которые натянули генерики(здарова), типа наш адт работает с N неизвестными параметрами и это все разнесено по членам суммы
sealed trait Foo[+A, +B]
case class Bar[+A, +B](a: A, b: B) extends Foo[A, B]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

это простой АДТ или уже ГАДТ?
источник

R

RattenK 🍄🐀🌹 in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
sealed trait Foo[+A, +B]
case class Bar[+A, +B](a: A, b: B) extends Foo[A, B]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

это простой АДТ или уже ГАДТ?
для меня и исходя из моего определения — гадт
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
RattenK 🍄🐀🌹
для меня и исходя из моего определения — гадт
неправильный ответ
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
это простой АДТ, у всех конструкторов тот же набор тайп-параметров, что и у типа
источник

NV

Nikita Vilunov in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
sealed trait Foo[+A, +B]
case class Bar[+A, +B](a: A, b: B) extends Foo[A, B]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

это простой АДТ или уже ГАДТ?
читаемость класс
источник

R

RattenK 🍄🐀🌹 in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
а, типа если я сделаю Quax[+A, +B, +C], то уже гадт?
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
sealed trait Foo[+A, +B]
case class Bar[+A](a: A) extends Foo[A, String]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

вот это, например ГАДТ
источник

NV

Nikita Vilunov in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
если ты сделаешь case object Kek extends Foo[Int, String]
источник

GP

Grigory Pomadchin in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
RattenK 🍄🐀🌹
а, типа если я сделаю Quax[+A, +B, +C], то уже гадт?
не, тип у тя типы разные должны быть
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
sealed trait Foo[+A, +B]
case class Bar[+A, +B, C](c: C, f: C => (A, B)) extends Foo[A, B]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

и
это тоже ГАДТ
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
соответственно эти два примера связаны с разными механизмами, которые представлены в конпеляторах
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
когда ты пишешь
(foo : Foo[A, B]) match {
 case Bar(a, b)
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
в случае АДТ ничего особенного не происходит с типами, у тебя просто появляются в контексте два новых имени
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
sealed trait Foo[+A, +B]
case class Bar[+A](a: A) extends Foo[A, String]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

вот это, например ГАДТ
если ты пишешь case Bar(a) => в этом случае происходит то, что в конпеляторах называется унификация, т.е. компилятор узнает, что B = String , унифицирует два типа
и использует это в других своих выводах
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
Oleg ℕizhnik
sealed trait Foo[+A, +B]
case class Bar[+A, +B, C](c: C, f: C => (A, B)) extends Foo[A, B]
case class Baz[+A, +B](la: List[A], lb: List[B]) extends Foo[A, B]

и
это тоже ГАДТ
если ты пишешь
case Bar(c, f) =>  в этом случае у тебя происходит другой эффект - ты знаешь, что во время конструкции был какой-то тип, и этот тип важен, чтобы расставить типы для с и f
например, ты должен знать что f можно применить к с а инту - без доп информации нельзя
т.е. конструктор можно представить как ∃C . c : C, f: C => (A, B)
такие типы называются экзистенциальными, и во время патерн-матчинга конпелятор делает другой трюк - это притворяется, что этот блок находится внутри какой-то генерик\параметрического контекста, где есть абстрактный тип С, т.е. как будто бы ты объявил
def handleBar[C](c: C, f: C => (A, B)) = ... с телом твоего матча
такой процесс выворачивания экзистенциальных типов в универсальные определения называется сколемизацией
источник

Oℕ

Oleg ℕizhnik in ПОКА ОДЕРСКИ НЕ ВИДИТ (спидран Олега по тофу)
вот вся эта хуита работает в дотти более или менее хорошо
в 2.13 приемлемо, а в 2.12 иногда не работает, а иногда приводит к крашам компилятор
источник