Skip to content

Add extension instances #8318

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 11 commits into from
Mar 3, 2020

Conversation

odersky
Copy link
Contributor

@odersky odersky commented Feb 14, 2020

Add a new extension { ... } syntax for extension instances without a collective parameter, and
tweak the translation rules for collective extensions.

Motivation

Collective extensions and normal extension methods are conceptually closely related, but look far apart. The expansion of collective extensions into given instances that implement AnyRef is a cute technical trick, but few would want to write that.

It is generally encouraged that extension methods should be put into given instances since that way they can be often be found in the implicit scope of the left-hand side argument, and do not require an import. Furthermore, it's better to import an implicit extension object instead of all extension methods since that leads to less namespace pollution.

But so far, the only pleasant way to do this was to use collective extensions. These are great where they fit, but they do not fit everything. In particular, one sometimes wants to define a bunch of extension methods that do not share a common left parameter. Then one would have to define a separate collective extension for each extension method, which is also awkward.

Summary

This PR adds extension instances, to address the above mentioned shortcomings. Extension instances are simply extensions without the on part. Example:

extension ops {
  def (xs: Seq[String]).longestStrings: Seq[String] = {
    val maxLength = xs.map(_.length).max
    xs.filter(_.length == maxLength)
  }
  def [T](xs: List[T]).second: T = xs.tail.head
}

This extension groups the two extension methods longestStrings and second into a single given instance ops.

Collective extensions are mapped to extension instances by repeating the common parameter and extension instances are mapped in turn to given instances.

New doc page: https://github.com/lampepfl/dotty/blob/d36f43bc9ae1bc28fd5ade8d1fcfd7d14365301c/docs/docs/reference/contextual/extension-methods.md

@odersky odersky force-pushed the add-extension-instance branch 2 times, most recently from 071b0b4 to d36f43b Compare February 15, 2020 11:49
@odersky odersky changed the title Trial: extension instances Add extension instances Feb 15, 2020
@odersky odersky force-pushed the add-extension-instance branch from d36f43b to ee3a2ac Compare February 15, 2020 22:57
@odersky odersky force-pushed the add-extension-instance branch from ee3a2ac to 865604a Compare February 29, 2020 17:10
@odersky odersky force-pushed the add-extension-instance branch from 2152fba to 2c88bb5 Compare March 2, 2020 08:11
I believe error messages tests should be dropped, unless they test something really specific.
E.g. a way information is represented that is easy to break.

For normal tests we have check files, or (most of the time even better) `// error` annotations.

The problem with over-engineered solutions like error messages tests is that they cause a huge
friction when things change. I lost an inordinate amount of time getting the extensions PR
over the line since in the meantime there landed an elaborate error messages commit. Fixing rebase
breakages over this PR is not a good use of my time! Two things could improve that situation:

 - we go slower on inessential PRs like error messages, _in particular_ if there is a pending
   conflict with a pending PR
 - we go faster merging essential PRs.
@odersky odersky requested a review from anatoliykmetyuk March 2, 2020 11:08
@odersky odersky added the fasttrack Simple fix. Reviewer should merge or apply additional changes directly. label Mar 2, 2020
@anatoliykmetyuk anatoliykmetyuk merged commit b448db2 into scala:master Mar 3, 2020
@anatoliykmetyuk anatoliykmetyuk deleted the add-extension-instance branch March 3, 2020 15:04
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
fasttrack Simple fix. Reviewer should merge or apply additional changes directly.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants