Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Recursive structural types #5355

Closed
scabug opened this issue Jan 4, 2012 · 5 comments
Closed

Recursive structural types #5355

scabug opened this issue Jan 4, 2012 · 5 comments

Comments

@scabug
Copy link

scabug commented Jan 4, 2012

There have been a few StackOverflow questions related to recursive structural types, the answer to which is generally "Scala doesn't do that; use typeclasses instead."

Simple example:

type Num = {
  def +(n: Num): Num
}

I found #3165, but it wasn't clear to me whether this duplicates that issue...

@scabug
Copy link
Author

scabug commented Jan 4, 2012

Imported From: https://issues.scala-lang.org/browse/SI-5355?orig=1
Reporter: Dan Rosen (mergeconflict)

@scabug
Copy link
Author

scabug commented Jan 4, 2012

@soc said:
At least the error message could be improved a bit, imho.

@scabug
Copy link
Author

scabug commented Jan 5, 2012

Dan Rosen (mergeconflict) said:
bq. At least the error message could be improved a bit, imho.

Hey Simon, did you mean to add this to SI-5356? If not, then I totally agree with you ;)

@scabug
Copy link
Author

scabug commented Dec 4, 2012

@milessabin said:
This is a duplicate of #967, surely.

As an aside, it's possible to encode your way around the problem if you're really desperate,

// Gilles' fix for SI-967 causes the definition of Nat to be rejected with
// the error "Parameter type in structural refinement may not refer to a type
// member of that refinement". However we can work around the problem by 
// quantifying out the problematic parameter type and reinstating it via
// a generalized type constraint.

type Num = {
  type Rep
  val zero : Rep
  def succ[R](r : R)(implicit ev : R =:= Rep) : Rep
  def show[R](r : R)(implicit ev : R =:= Rep) : String
}

val IntNum : Num = new {
  type Rep = Int
  val zero = 0
  def succ[R](r : R)(implicit ev : R =:= Rep) : Rep = r+1
  def show[R](r : R)(implicit ev : R =:= Rep) = r.toString
}

val DoubleNum : Num = new {
  type Rep = Double
  val zero = 0.0
  def succ[R](r : R)(implicit ev : R =:= Rep) : Rep = r+1.0
  def show[R](r : R)(implicit ev : R =:= Rep) = r.toString
}

def two(n : Num) = n.show(n.succ(n.succ(n.zero)))

scala> two(IntNum)
res0: String = 2

scala> two(DoubleNum)
res1: String = 2.0

@scabug
Copy link
Author

scabug commented Dec 4, 2012

@retronym said:
This one is only open to give a more targeted error message.

@scabug scabug added this to the Backlog milestone Apr 7, 2017
Jasper-M added a commit to Jasper-M/scala that referenced this issue Jun 30, 2017
The pattern match in TypeDiagnostics also matched methods in structural types that do have a return type.
Strictly match on vals and defs with an empty TypeTree as return type. Show the default error message otherwise.
Fixes scala/bug#5355
@scala scala deleted a comment from scabug Jul 5, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants