Skip to content

Experimental Support for Dependent Type Arguments - Step 1: Parsing #8863

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

Merged
merged 9 commits into from
May 26, 2020

Conversation

odersky
Copy link
Contributor

@odersky odersky commented May 3, 2020

This PR introduces syntax and parsing for dependent type arguments. The plan is that these additions should eventually replace the current unsafe use of Singleton.

Two syntax forms:

Application: Types like

Vec[String](n)
Vec[String](10)

Type Abstraction :

type Vec[T] = (x: Int) =>> ...
type Vec[T](n: Int) = ...

Together:

type Matrix[T](m: Int, n: Int) = Vec[Vec[T](n)](m)

This is supported only under -language:experimental.dependent or the corresponding language import

import language.experimental.dependent

Types and typing rules are still missing, so actually using any of these (with the setting) will currently give "not yet implemented" errors in Typer.

Based on #8855

odersky added 9 commits May 1, 2020 12:13
No need to start a separate scanner; we can simply use the existing prev/next logic.
Instead of passing a closure down, use one-token lookahead going froward.
This simplifies the logic of parsing paths.
Split off the parts of SimpleType that

 - can be applied to type arguments, or selected with #
 - can be used in a constructor

This gives a bit more precision for type and constructor parsing.
It's also a necessary step to be able to add types that are applied to
singletons.
@odersky
Copy link
Contributor Author

odersky commented May 3, 2020

So far missing is support for term-dependent higher-kinded type parameters. For the time being it's better not to support them, at least until we have figured out the type inference situation.

@odersky odersky requested a review from rjraya May 10, 2020 08:21
@rjraya rjraya merged commit 266a1e4 into scala:master May 26, 2020
@anatoliykmetyuk anatoliykmetyuk deleted the depscala-2 branch June 12, 2020 13:23
@bblfish
Copy link

bblfish commented Aug 23, 2020

I came across this PR whilst trying to port banana-rdf to dotty.
I have a trait RDF { ... } which just specifies all the types needed for RDF. These then get implementations specifying types for existing RDF libraries.

In the current banana-rdf we use type projections, which no longer work. See my question on scala community for details.

I have been looking to see if I could just use implicits like this:

class PointedGraph(using val rdf: RDF)(pointer: rdf.Node, graph: rdf.Graph)

which is not that far from what we had before

class PointedGraph[Rdf<:RDF]( pointer: Rdf#Node, graph: Rdf#Graph)

But this leads to the following problem with code like this:

class PointedGraphs(using val ops: RDFOps)(
  val nodes: Iterable[ops.Rdf.Node], 
  val graph: ops.Rdf.Graph
) extends Iterable[PointedGraph] {
  import ops.Rdf

The problem is that the extends clause Iterable[PointedGraph] no longer has information about the ops type. And so we would need to pass that along in the definition and the methods like this:

 def /(p: Rdf.URI): PointedGraphs(ops) = {
    val ns: Iterable[Rdf.Node] = this flatMap { (pointed: PointedGraph) =>
      import pointed.pointer
      ops.getObjects(graph, pointer, p)
    }
    new PointedGraphs()(ns, graph)  // note though that one needs an extra () for the implicit
  }

If one adds the type info back then one now has double the work: one has to both keep track of the types, and also pass around the implicit object.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants