Skip to content

Commit 0cfd797

Browse files
committed
Add doc page
1 parent 259ecea commit 0cfd797

File tree

4 files changed

+131
-1
lines changed

4 files changed

+131
-1
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,118 @@
1+
---
2+
layout: doc-page
3+
title: Rules for Operators
4+
---
5+
6+
There are two annotations that regulate operators: `infix` and `alpha`.
7+
8+
## The @alpha Annotation
9+
10+
An `@alpha` annotation on a method definition defines an alternate name for the implementation of that method: Example:
11+
```scala
12+
object VecOps {
13+
@alpha("append") def (xs: Vec[T]) ++= [T] (ys: Vec[T]): Vec[T] = ...
14+
}
15+
```
16+
Here, the `++=` operation is implemented (in Byte code or native code) under the name `append`. The implementation name affects the code that is generated, and is the name under which code from other languages can call the method. For instance, `++=` could be invoked from Java like this:
17+
```
18+
VecOps.append(vec1, vec2)
19+
```
20+
The `@alpha` annotation has no bearing on Scala usages. Any application of that method in Scala has to use `++=`, not `append`.
21+
22+
An `@alpha` annotation will be _mandatory_ if the method name is symbolic. Symbolic methods without `@alpha` annotations are deprecated.
23+
24+
### Motivation
25+
26+
The `@alpha` annotation serves a dual purpose:
27+
28+
- It helps interoperability between Scala and other languages.
29+
- It serves as a documentation tool by providing an alternative regular name
30+
as an alias of a symbolic operator.
31+
32+
### Details
33+
34+
1. `@alpha` is defined in package `scala.annotation`. It takes a single argument
35+
of type `String`. That string is called the _external name_ of the definition
36+
that's annotated.
37+
38+
2. An `@alpha` annotation can be given for all kinds of definitions.
39+
40+
3. The name given in an `@alpha` annotation must be a legal name
41+
for the defined entities on the host platform.
42+
43+
4. Definitions with symbolic names should have an `@alpha` annotation. Lack of such
44+
an annotation will raise a deprecation warning.
45+
46+
5. Definitions with names in backticks that are not legal host platform names
47+
should have an `@alpha` annotation. Lack of such an annotation will raise a deprecation warning.
48+
49+
6. @alpha annotations must agree: If two definitions are members of an object or class with the same name and matching types, then either none of them has an `@alpha` annotation, or both have `@alpha` annotations with the same name.
50+
51+
7. There must be a one-to-one relationship between external and internal names:
52+
If two definitions are members of an object or class with matching types and both have `@alpha` annotations with the same external name, then their internal method names must also be the same.
53+
54+
## The @infix Annotation
55+
56+
An `@infix` annotation on a method definition allows using the method as an infix operation. Example:
57+
```scala
58+
trait MultiSet[T] {
59+
60+
@infix
61+
def union(other: MultiSet[T]): MultiSet[T]
62+
63+
def difference(other: MultiSet[T]): MultiSet[T]
64+
65+
@alpha("intersection")
66+
def *(other: MultiSet[T]): MultiSet[T]
67+
}
68+
69+
val s1, s2: MultiSet[Int]
70+
71+
s1 union s2 // OK
72+
s1.union(s2) // also OK
73+
74+
s1.difference(s2) // OK
75+
s1 `difference` s2 // OK
76+
s1 difference s2 // gives a deprecation warning
77+
78+
s1 * s2 // OK
79+
s1.*(s2) // also OK, but unusual
80+
```
81+
Infix operations involving alphanumeric operators that do not carry @infix annotations are deprecated. Infix operations involving symbolic operators are always allowed, so `@infix` is redundant for methods with symbolic names. Infix operations are also allowed
82+
if an alphanumeric operator name is given in backticks (as in the third call of `difference` above).
83+
84+
The @infix annotation can also be given to a type:
85+
```
86+
@infix type or[X, Y]
87+
val x: String or Int = ...
88+
```
89+
90+
### Motivation
91+
92+
The purpose of the `@infix` annotation is to achieve consistency across a code base in how a method or type is applied. The idea is that the author of a method decides whether that method should be applied as an infix operator or in a regular application. Use sites then implement that decision consistently.
93+
94+
### Details
95+
96+
1. `@infix` is defined in package `scala.annotation`.
97+
98+
2. If a method overrides another, their infix annotations must agree. Either both are annotated with `@infix`, or none of them are.
99+
100+
3. `@infix` annotations can be given to method definitions. The first non-receiver parameter list of an `@infix` method must define exactly one parameter. Examples:
101+
102+
```scala
103+
@infix def op(x: S): R // ok
104+
@infix def op[T](x: T)(y: S): R // ok
105+
@infix def op[T](x: T, y: S): R // error: two parameters
106+
107+
@infix def (x: A) op (y: B): R // ok
108+
@infix def (x: A) op (y1: B, y2: B): R // error: two parameters
109+
```
110+
111+
4. @infix annotations can also be given to type, trait or class definitions that have exactly two type parameters. An infix type like
112+
113+
```scala
114+
@infix type op[X, Y]
115+
```
116+
117+
can be applied using infix syntax, i.e. `A op B`.
118+

docs/sidebar.yml

+2
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,8 @@ sidebar:
9191
url: docs/reference/changed-features/lazy-vals.html
9292
- title: Structural Types
9393
url: docs/reference/changed-features/structural-types.html
94+
- title: Operators
95+
url: docs/reference/changed-features/operators.html
9496
- title: Type Checking
9597
url: docs/reference/changed-features/type-checking.html
9698
- title: Type Inference
+7-1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
11
package scala.annotation
22

3-
final class alpha(name: String) extends StaticAnnotation
3+
/** An annotation that defines an external name for a definition.
4+
* If an `alpha(extname)` annotation is given for a method or some other
5+
* definition, its implementation will use the name `extname` instead of
6+
* the regular name. An `alpha` annotation is mandatory for definitions
7+
* with symbolic names.
8+
*/
9+
final class alpha(externalName: String) extends StaticAnnotation
+4
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
11
package scala.annotation
22

3+
/** A method annotation that suggests that the annotated method should
4+
* be used as an infix operator. Infix operations with alphanumeric
5+
* operator names require the operator to be annotated with `@infix`.
6+
*/
37
final class infix extends StaticAnnotation

0 commit comments

Comments
 (0)