diff options
Diffstat (limited to 'doc/reference/reference.verb.tex')
-rw-r--r-- | doc/reference/reference.verb.tex | 5025 |
1 files changed, 0 insertions, 5025 deletions
diff --git a/doc/reference/reference.verb.tex b/doc/reference/reference.verb.tex deleted file mode 100644 index dff170c2d7..0000000000 --- a/doc/reference/reference.verb.tex +++ /dev/null @@ -1,5025 +0,0 @@ -% $Id$ - -\documentclass[11pt]{report} - -\usepackage{fleqn,a4,modefs,math,prooftree,scaladefs,vquote} - -\newcommand{\ifqualified}[1]{} -\newcommand{\iflet}[1]{} -\newcommand{\ifundefvar}[1]{} -\newcommand{\iffinaltype}[1]{} -\newcommand{\ifpackaging}[1]{} -\newcommand{\ifnewfor}[1]{} -\renewcommand{\todo}[1]{{$\clubsuit$\bf todo: #1$\spadesuit$}} -\newcommand{\notyet}{\footnote{not yet implemented.}} -\title{Report on the Programming Language Scala} - -\date{\today} - -\author{ -Martin Odersky \\ -Philippe Altherr \\ -Vincent Cremet \\ -Burak Emir \\ -St\'ephane Micheloud \\ -Nikolay Mihaylov \\ -Michel Schinz \\ -Erik Stenman \\ -Matthias Zenger -\\ \ -\\ -EPFL} - - -\sloppy -\begin{document} -\maketitle - -%\todo{`:' as synonym for $\EXTENDS$?} - -\chapter{Rationale} - -\input{rationale-chapter} - -\comment{ -\chapter{Change Log} - -5 August 2001: Changed from join patterns in function definitions to -when clauses. - -5 August 2001: Introduced guard part in case expressions. - -5 August 2001: Dropped overload modifier. - -5 August 2001: Dropped \verb@=>@ as an alternative for \verb@=@ in -definitions. - -5 August 2001: Dropped \verb@nil@ type. - -5 August Replaced \verb@&@ operator for parallel composition by -\verb@fork@ function. - -5 August 2001: Added chapter on Concurrency (\sref{sec:concurrency}). - -7 August 2001: Made explicit in the grammar that block-local -definitions do not have modifiers. - -7 August 2001: Introduced permitted but redundant modifier `private' -for guards. - -9 August 2001: Replaced qualified identifiers in class definitions by -modifiers \verb@new@ and \verb@override@. - -9 August 2001: Tightened rules for member access, so that superclass -ordering is irrelevant. See definition of qualified expansion in -\sref{sec:names}. - -9 August 2001: Guarded choice now always picks tectually first enabled -guard, rather than an arbitrary one. - -16 August 2001: Unary postfix operators now have lower precedence than -unary infix. - -16 August 2001: Use `=' instead of `:=' for assignment. - -16 August 2001: Changed scope rules so that scope of a definition -always extends to the whole enclosing block or template, plus an -anti forward-dependency rule for value definitions. - -16 August 2001: Changed Grammar to allow repeated data definitions -only with extends clauses of simple type, so that parameter names -cannot be used. - -16 August 2001: Changed Grammar to drop NxStat, etc (the context-free language -is not affected by the change). - -23 August 2001: Eliminated unboxed types. - -23 August 2001: Eliminated recursive value definitions; changed rules - for pattern value definitions. - -26 August 2001: Clarified indentation rules. - -26 August 2001: Adapted meaning of \verb@null@ to value types. - -26 August 2001: Apply local type inference in class instance expressions. - -23 Sep 2001: Changed $\arrow$ in closures to $\Arrow$. - -23 Sep 2001: Changed record types to refinements. - -25 Oct 2001: Simplified and generalized class and module -design. Classes and modules can now appear anywhere; modules are no -longer parameterized. - -25 Oct 2001: Dropped aspects (for the time being). - -29 Oct 2001: - Tuple and function types are now shorthands for predefined - classes. Tuples are no longer covariant. - -29 Oct 2001: - Introduced $n$-ary functions and changed syntax for function types. - -29 Oct 2001: - Dropped static part of classes. Classes now define a constructor - function of the same name. - -29 Oct 2001: - Generalized rules for overloading slightly. - -29 Oct 2001: - Dropped modifiers for guards. - -29 Oct 2001: - Disambiguated syntax for pattern matching cases with guards. -class P[+a, +b] { - val fst: a, snd: b -} - -2 Nov 2001: Changed private and protected to their meaning in Java. - -2 Nov 2001: Introduced packagings. - -5 Nov 2001: Dropped value parameters in class aliases. - -14 Nov 2001: Fixed rule for subtyping of overloaded -function. Tightened scope of value parameters. - -15 Nov 2001: Changed `with' to `if' as pattern guard and simplified -pattern syntax. - -15 Nov 2001: Changed `data' to `case class'. - -20 Nov 2001: Case classes need no longer be `final'. - -30 Nov 2001: Introduced `qualified' classes, with unqualified classes -being the default. - -4 Dec 2001: Introduced interfaces (\sref{sec:interfaces}) - -4 Dec 2001: Changed rules which members are inherited (\sref{sec:members}). - -4 Dec 2001: Changed rules for compound types with refinements to match -those for templates (\sref{sec:compound-types}). - -6 Dec 2001: Dropped modifiers `virtual' and `new'. - -6 Dec 2001: `new' is again mandatory in instance creation expressions. - -10 Dec 2001: Dropped concurrency constructs in language. - -11 Dec 2001: Changed name from `Funnel' to `Scala'. - -18 Dec 2001: Slight change of syntax for anonymous functions. - -29 Dec 2001: Case classes define accessors for parameters - -6 Feb 2002: Import clauses defined only for stable identifiers. - -6 Feb 2002: Dropped restriction that classes may not have -inherited abstract members. - -6 Feb 2002: Reclassified `new' as Expr4 - -6 Feb 2002: Dropped interface keyword - -6 Feb 2002: Changed syntax of `if'. - -6 Feb 2002: Introduced constructor types. - -6 Feb 2002: Eliminated class aliases. - -6 Feb 2002: Replaced user-defined value definitions by comprehensions. - -6 Feb 2002: Tightened conditions on well-formed base class sequence. - -6 Feb 2002: Changed root class hierarchy. - -7 Feb 2002: Tightened rules on forward references. - -7 Feb 2002: Only prefix operators are now `-', `+', `!'. They are -translated to method calls of their operand. -} - -class List[a <: AnyRef](x: a, xs: List[a]) { - def head = x; - def tail = xs; - def this(x: a) = { ... ; this(x, Nil); ... } - def this() = this(null, Nil); -} - - - - -% 16 Jul 2003 Regular pattern matching (Chapter 8) - -\subsection*{Status of This Document} - -The present document defines slightly more than what is implemented in -the current compiler. But I have tried to mark all omissions that -still exist. - -\part{Language Definition} - -\chapter{Lexical Syntax} - -This chapter defines the syntax of Scala tokens. Tokens are -constructed from symbols in the following character sets: -\begin{enumerate} -\item Whitespace characters. -\item Lower case letters \verb@`a' | ... | `z'@ and -upper case letters \verb@`A' | ... | `Z' | `$\Dollar$' | `_'@. -\item Digits \verb@`0' | ... | `9'@. -\item Parentheses \verb@`(' | `)' | `[' | `]' | `{' | `}'@. -\item Delimiter characters \verb@`\' | `'' | `"' | `.' | `;' | `,'@. -\item Operator characters. These include all printable ASCII characters -which are in none of the sets above. -\end{enumerate} - -These sets are extended in the usual way to unicode\notyet (i.e.\ as in Java). -Unicode encodings \verb@`\uXXXX'@ are also as in Java. - -\section{Identifiers} - -\syntax\begin{verbatim} -op \=::= \= special {special} [`_' [id]] -varid \>::= \> lower {letter $|$ digit} [`_' [id]] -id \>::= \> upper {letter $|$ digit} [`_' [id]] - \> | \> varid - \> | \> op -\end{verbatim} - -There are two ways to form an identifier. First, an identifier can -start with a letter which can be followed by an arbitrary sequence of -letters and digits. Second, an identifier can be start with a special -character followed by an arbitrary sequence of special characters. -In both cases, the identifier prefix may be immediately followed -by an underscore `\verb@_@' character and another string of characters -that by themselves make up an identifier. As usual, a longest match -rule applies. For instance, the string - -\begin{verbatim} -big_bob++=z3 -\end{verbatim} - -decomposes into the three identifiers \verb@big_bob@, \verb@++=@, and -\verb@z3@. The rules for pattern matching further distinguish between -{\em variable identifiers}, which start with a lower case letter, and -{\em constant identifiers}, which do not. - - -The `\verb@\$@' character is reserved for compiler-synthesized identifiers. -User programs are not allowed to define identifiers which contain `\verb@\$@' -characters. - -The following names are reserved words instead of being members of the -syntactic class \verb@id@ of lexical identifiers. - -\begin{verbatim} -abstract case catch class def -do else extends false final -finally for if import new -null object override package private -protected return sealed super this -trait try true type val -var while with yield -_ : = => <- <: >: # @ -\end{verbatim} - -The unicode operator `\verb@=>@' has the ascii equivalent -`$=>$', which is also reserved\notyet. - -\example -Here are examples of identifiers: -\begin{verbatim} - x \=Object \=maxIndex \=p2p \=empty_? - + \> +_field -\end{verbatim} - -\section{Braces and Semicolons} - -A semicolon `\verb@;@' is implicitly inserted after every closing brace -if there is a new line character between closing brace and the next -regular token after it, except if that token cannot legally start a -statement. - -The tokens which cannot legally start a statement -are the following delimiters and reserved words: -\begin{verbatim} -else extends with yield do -, . ; : = => <- <: >: # @ ) ] } -\end{verbatim} - -\section{Literals} - -There are literals for integer numbers (of types \verb@Int@ and \verb@Long@), -floating point numbers (of types \verb@Float@ and \verb@Double@), characters, and -strings. The syntax of these literals is in each case as in Java. - -\syntax\begin{verbatim} -literal \=::= \= intLit - \> | \> floatLit - \> | \> charLit - \> | \> stringLit - \> | \> symbolLit -intLit \>::= \> ``as in Java'' -floatLit \>::= \> ``as in Java'' -charLit \>::= \> ``as in Java'' -stringLit \>::= \> ``as in Java'' -symbolLit ::= `\'` id -\end{verbatim} - -A symbol literal has the form \verb@'x@ where \verb@x@ is an identifier. -Such a symbol literal is a shorthand for the application -\begin{verbatim} -scala.Symbol("x") -\end{verbatim} -of the facotry method for the standard case class \verb@Symbol@ to the string "x". - -\section{Whitespace and Comments} - -Tokens may be separated by whitespace characters (ascii codes 0 to 32) -and/or comments. Comments come in two forms: - -A single-line comment is a sequence of characters which starts with -\verb@//@ and extends to the end of the line. - -A multi-line comment is a sequence of characters between \verb@/*@ and -\verb@*/@. Multi-line comments may be nested. - - -\chapter{\label{sec:names}Identifiers, Names and Scopes} - -Names in Scala identify types, values, functions, and classes which -are collectively called {\em entities}. Names are introduced by -definitions, declarations (\sref{sec:defs}) or import clauses -(\sref{sec:import}), which are collectively called {\em binders}. - -There are two different name spaces, one for types (\sref{sec:types}) -and one for terms (\sref{sec:exprs}). The same name may designate a -type and a term, depending on the context where the name is used. - -A definition or declaration has a {\em scope} in which the entity -defined by a single name can be accessed using a simple name. Scopes -are nested, and a definition or declaration in some inner scope {\em -shadows} a definition in an outer scope that contributes to the same -name space. Furthermore, a definition or declaration shadows bindings -introduced by a preceding import clause, even if the import clause is -in the same block. Import clauses, on the other hand, only shadow -bindings introduced by other import clauses in outer blocks. - -A reference to an unqualified (type- or term-) identifier $x$ is bound -by the unique binder, which -\begin{itemize} -\item defines an entity with name $x$ in the same namespace as the -identifier, and -\item shadows all other binders that define entities with name $x$ in that namespace. -\end{itemize} -It is an error if no such binder exists. If $x$ is bound by an import -clause, then the simple name $x$ is taken to be equivalent to the -qualified name to which $x$ is mapped by the import clause. If $x$ is bound by a definition or declaration, -then $x$ refers to the entity introduced by that -binder. In that case, the type of $x$ is the type of the referenced -entity. - -\example Consider the following nested definitions and imports: - -\begin{verbatim} -object m1 { - object m2 { val x: int = 1; val y: int = 2 } - object m3 { val x: boolean = true; val y: String = "" } - val x: int = 3; - { import m2._; \= // shadows nothing - \> // reference to `x' is ambiguous here - val x: String = "abc"; \> // shadows preceding import and val - \> // `x' refers to latest val definition - { import m3._ \> // shadows only preceding import m2 - \> // reference to `x' is ambiguous here - \> // `y' refers to latest import clause - } - } -} -\end{verbatim} - -A reference to a qualified (type- or term-) identifier $e.x$ refers to -the member of the type $T$ of $e$ which has the name $x$ in the same -namespace as the identifier. It is an error if $T$ is not an object type -(\sref{def:object-type}). The type of $e.x$ is the member type of the -referenced entity in $T$. - -\chapter{\label{sec:types}Types} - -\syntax\begin{verbatim} - Type \=::= \= Type1 `=>' Type - \> |\> `(' [Types] `)' `=>' Type - \> |\> Type1 - Type1 \>::= \> SimpleType {with SimpleType} [Refinement] - SimpleType \>::= \> StableId - \> |\> SimpleType `#' id - \> |\> Path `.' type - \> |\> SimpleType TypeArgs - \> |\> `(' Type ')' - Types \>::= \> Type {`,' Type} -\end{verbatim} - -We distinguish between first-order types and type constructors, which -take type parameters and yield types. A subset of first-order types -called {\em value types} represents sets of (first-class) values. -Value types are either {\em concrete} or {\em abstract}. Every -concrete value type can be represented as a {\em class type}, i.e.\ a -type designator (\sref{sec:type-desig}) that refers to a -class\footnote{We assume that objects and packages also -implicitly define a class (of the same name as the object or package, -but inaccessible to user programs).} (\sref{sec:classes}), -or as a {\em compound type} (\sref{sec:compound-types}) -consisting of class types and possibly -also a refinement (\sref{sec:refinements}) that further constrains the -types of its members. - -A shorthands exists for denoting function types -(\sref{sec:function-types}). Abstract value types are introduced by -type parameters and abstract type bindings (\sref{sec:typedcl}). -Parentheses in types are used for grouping. - -Non-value types capture properties of -identifiers that are not values -(\sref{sec:synthetic-types}). There is no syntax to express these -types directly in Scala. - -\section{Paths}\label{sec:paths} - -\syntax\begin{verbatim} - StableId \=::= \= id - \> |\> Path `.' id - \> |\> [id '.'] super [`[' id `]'] `.' id - Path \>::=\> StableId - \> |\> [id `.'] this -\end{verbatim} - -Paths are not types themselves, but they can be a part of named types -and in that way form a central role in Scala's type system. - -A path is one of the following. -\begin{itemize} -\item -The empty path $\epsilon$ (which cannot be written explicitly in user programs). -\item -\verb@C.this@, where \verb@C@ references a class. -The path \verb@this@ is taken as a shorthand for \verb@C.this@ where -\verb@C@ is the class directly enclosing the reference. -\item -\verb@p.x@ where \verb@p@ is a path and \verb@x@ is a stable member of \verb@p@. -{\em Stable members} are members introduced by value or object -definitions, as well as packages. -\item -\verb@C.super.x@ or \verb@C.super[M].x@ -where \verb@C@ references a class and \verb@x@ references a -stable member of the super class or designated mixin class \verb@M@ of \verb@C@. -The prefix \verb@super@ is taken as a shorthand for \verb@C.super@ where -\verb@C@ is the class directly enclosing the reference. -\end{itemize} -A {\em stable identifier} is a path which ends in an identifier. - -\section{Value Types} - -\subsection{Singleton Types} -\label{sec:singleton-type} - -\syntax\begin{verbatim} - SimpleType ::= Path `.' type -\end{verbatim} - -A singleton type is of the form \verb@p.type@, where \verb@p@ is a -path. The type denotes the set of values consisting of -exactly the value denoted by \verb@p@. - -\subsection{Type Projection} -\label{sec:type-project} - -\syntax\begin{verbatim} -SimpleType ::= SimpleType `#' id -\end{verbatim} - -A type projection \verb@T#x@ references the type member named -\verb@x@ of type \verb@T@. \verb@T@ must be either a singleton type, -or a non-abstract class type, or a Java class type (in either of the -last two cases, it is guaranteed that \verb@T@ has no abstract type -members). - -\subsection{Type Designators} -\label{sec:type-desig} - -\syntax\begin{verbatim} - SimpleType ::= StableId -\end{verbatim} - -A type designator refers to a named value type. It can be simple or -qualified. All such type designators are shorthands for type projections. - -Specifically, the unqualified type name $t$ where $t$ is bound in some -class, object, or package $C$ is taken as a shorthand for -\verb@C.this.type#t@. If $t$ is not bound in a class, object, or -package, then \verb@t@ is taken as a shorthand for -\verb@$\epsilon$.type#t@. - -A qualified type designator has the form \verb@p.t@ where \verb@p@ is -a path (\sref{}) and $t$ is a type name. Such a type designator is -equivalent to the type projection \verb@p.type#x@. - -\example -Some type designators and their expansions are listed below. We assume -a local type parameter \verb@t@, a value \verb@mytable@ -with a type member \verb@Node@ and the standard class \verb@scala.Int@, -\begin{verbatim} - t \=$\epsilon$.type#t - Int \>scala.type#Int - scala.Int \>scala.type#Int - mytable.Node \>mytable.type#Node -\end{verbatim} - -\subsection{Parameterized Types} -\label{sec:param-types} - -\syntax\begin{verbatim} - SimpleType \=::= \= SimpleType TypeArgs - TypeArgs \>::= \> `[' Types `]' -\end{verbatim} - -A parameterized type $T[U_1, ..., U_n]$ consists of a type designator -$T$ and type parameters $U_1 \commadots U_n$ where $n \geq 1$. $T$ -must refer to a type constructor which takes $n$ type parameters $a_1, -..., a_n$ with lower bounds $L_1, ..., L_n$ and upper bounds $U_1, -..., U_n$. - -The parameterized type is well-formed if each actual type parameter -{\em conforms to its bounds}, i.e.\ $L_i\sigma <: T_i <: U_i\sigma$ where $\sigma$ -is the substitution $[a_1 := T_1, ..., a_n := T_n]$. - -\example\label{ex:param-types} -Given the partial type definitions: - -\begin{verbatim} - class TreeMap[a <: Ord[a], b] { ... } - class List[a] { ... } - class I extends Ord[I] { ... } -\end{verbatim} - -the following parameterized types are well formed: - -\begin{verbatim} - HashMap[I, String] - List[I] - List[List[Boolean]] -\end{verbatim} - -\example Given the type definitions of \ref{ex:param-types}, -the following types are ill-formed: - -\begin{verbatim} - HashMap[I] \=// illegal: wrong number of parameters - HashMap[List[I], Boolean] \>// illegal: type parameter not within bound -\end{verbatim} - -\subsection{Compound Types} -\label{sec:compound-types} - -\syntax\begin{verbatim} - Type \=::= \= SimpleType {with SimpleType} [Refinement] - Refinement \>::=\> `{' [RefineStat {`;' RefineStat}] `}' - RefineStat \>::=\> Dcl - \> |\> type TypeDef {`,' TypeDef} - \> |\> -\end{verbatim} - -A compound type \verb@T$_1$ with ... with T$_n$ {R}@ represents -objects with members as given in the component types $T_1 \commadots -T_n$ and the refinement \verb@{R}@. Each component type $T_i$ must be a -class type and the base class sequence generated by types $T_1 -\commadots T_n$ must be well-formed (\sref{sec:basetypes-wf}). A -refinement \verb@{R}@ contains declarations and type -definitions. Each declaration or definition in a refinement must -override a declaration or definition in one of the component types -$T_1 \commadots T_n$. The usual rules for overriding (\sref{}) -apply. If no refinement is given, the empty refinement is implicitly -added, i.e. \verb@T$_1$ with ... with T$_n$@ is a shorthand for -\verb@T$_1$ with ... with T$_n$ {}@. - -\subsection{Function Types} -\label{sec:function-types} - -\syntax\begin{verbatim} - SimpleType \=::= \= Type1 `=>' Type - \> |\> `(' [Types] `)' `=>' Type -\end{verbatim} -The type \verb@(T$_1$, ..., T$_n$) => U@ represents the set of function -values that take arguments of types $T_1 \commadots T_n$ and yield -results of type $U$. In the case of exactly one argument type -\verb@S => T@ is a shorthand for \verb@(S) => T@. Function types -associate to the right, e.g.\ \verb@(S) => (T) => U@ is the same as -\verb@(S) => ((T) => U)@. - -Function types are shorthands for class types that define \verb@apply@ -functions. Specifically, the $n$-ary function type $(T_1 \commadots -T_n)U$ is a shorthand for the class type -\verb@Function$\,n$[$T_1 \commadots T_n$,U]@. Such class -types are defined in the Scala library for \verb@n@ between 0 and 9 as follows. -\begin{verbatim} -package scala; -trait Function$\,n$[-T$_1$, ..., -T$_n$, +R] { - def apply(x$_1$: T$_1$, ..., x$_n$: T$_n$): R; - override def toString() = "<function>"; -} -\end{verbatim} -Hence, function types are covariant in their result type, and -contravariant in their argument types. - -\section{Non-Value Types} -\label{sec:synthetic-types} - -The types explained in the following do not denote sets of values, nor -do they appear explicitely in programs. They are introduced in this -report as the internal types of defined identifiers. - -\subsection{Method Types} -\label{sec:method-types} - -A method type is denoted internally as $(Ts)U$, where $(Ts)$ is a -sequence of types $(T_1 \commadots T_n)$ for some $n \geq 0$ -and $U$ is a (value or method) type. This type represents named -methods that take arguments of types $T_1 \commadots T_n$ -and that return a result of type $U$. - -Method types associate to the right: $(Ts_1)(Ts_2)U$ is treated as -$(Ts_1)((Ts_2)U)$. - -A special case are types of methods without any parameters. They are -written here $[]T$, following the syntax for polymorphic method types -(\sref{sec:poly-types}). Parameterless methods name expressions that -are re-evaluated each time the parameterless method name is -referenced. - -Method types do not exist as types of values. If a method name is used -as a value, its type is implicitly converted to a corresponding -function type (\sref{sec:impl-conv}). - -\example The declarations -\begin{verbatim} -def a: Int -def b (x: Int): Boolean -def c (x: Int) (y: String, z: String): String -\end{verbatim} -produce the typings -\begin{verbatim} -a: [] Int -b: (Int) Boolean -c: (Int) (String, String) String -\end{verbatim} - -\subsection{Polymorphic Method Types} -\label{sec:poly-types} - -A polymorphic method type is denoted internally as \verb@[tps]T@ where -\verb@[tps]@ is a type parameter section -\verb@[a$_1$ <: L$_1$ >: U$_1$, ..., a$_n$ <: L$_n$ >: U$_n$] T@ -for some $n \geq 0$ and \verb@T@ is a -(value or method) type. This type represents named methods that -take type arguments \verb@S$_1$, ..., S$_n$@ which -conform (\sref{sec:param-types}) to the lower bounds -\verb@S$_1$, ..., S$_n$@ and the upper bounds -\verb@U$_1$, ..., U$_n$@ and that yield results of type \verb@T@. - -\example The declarations -\begin{verbatim} -def empty[a]: List[a] -def union[a <: Comparable[a]] (x: Set[a], xs: Set[a]): Set[a] -\end{verbatim} -produce the typings -\begin{verbatim} -empty \=: [a >: All <: Any] List[a] -union \>: [a >: All <: Comparable[a]] (x: Set[a], xs: Set[a]) Set[a] . -\end{verbatim} - -\subsection{Overloaded Types} -\label{sec:overloaded-types} -\newcommand{\overload}{\la\mbox{\sf and}\ra} - - -More than one values or methods are defined in the same scope with the -same name, we model - -An overloaded type consisting of type alternatives $T_1 \commadots -T_n$ $(n \geq 2)$ is denoted internally $T_1 \overload \ldots -\overload T_n$. - -\example The definitions -\begin{verbatim} -def println: unit; -def println(s: string): unit = ...; -def println(x: float): unit = ...; -def println(x: float, width: int): unit = ...; -def println[a](x: a)(tostring: a => String): unit = ... -\end{verbatim} -define a single function \verb@println@ which has an overloaded -type. -\begin{verbatim} -println: \= [] unit $\overload$ - \> (String) unit $\overload$ - \> (float) unit $\overload$ - \> (float, int) unit $\overload$ - \> [a] (a) (a => String) unit -\end{verbatim} - -\example The definitions -\begin{verbatim} -def f(x: T): T = ...; -val f = 0 -\end{verbatim} -define a function \verb@f@ which has type \verb@(x: T)T $\overload$ Int@. - -\section{Base Classes and Member Definitions} -\label{sec:base-classes} - -Types, bounds and base classes of class members depend on the way the -members are referenced. Central here are three notions, namely: -\begin{enumerate} -\item the notion of the base class sequence of a type $T$, -\item the notion of a type $T$ seen as a member of some class $C$ from some - prefix type $S$, -\item the notion of a member binding of some type $T$. -\end{enumerate} -These notions are defined mutually recursively as follows. - -1. The {\em base class sequence} of a type is a sequence of class types, -given as follows. -\begin{itemize} -\item -The base classes of a class type \verb@C@ are the base classes of class -\verb@C@. -\item -The base classes of an aliased type are the base classes of its alias. -\item -The base classes of an abstract type are the base classes of its upper bound. -\item -The base classes of a parameterized type \verb@C[T$_1$, ..., T$_n$]@ are the base classes -of type \verb@C@, where every occurrence of a type parameter $a_i$ -of \verb@C@ has been replaced by the corresponding parameter type $T_i$. -\item -The base classes of a singleton type \verb@p.type@ are the base classes of -the type of \verb@p@. -\item -The base classes of a compound type -\verb@T$_1$ with ... with T$_n$ with {R}@ is the concatenation of the -base classes of all \verb@T$_i$@'s, except that later base classes replace -earlier base classes which are instances of the same class. -\end{itemize} - -2. The notion of a type \verb@T@ -{\em seen as a member of some class \verb@C@ from some prefix type -\verb@S@} makes sense only if the prefix type \verb@S@ -has a type instance of class \verb@C@ as a base class, say -\verb@S'#C[T$_1$, ..., T$_n$]@. Then we define as follows. -\begin{itemize} - \item - If \verb@S = $\epsilon$.type@, then $T$ seen as a member of $C$ from $S$ is $T$ itself. - \item Otherwise, if \verb@T@ is the $i$'th type parameter of some class \verb@D@, then - \begin{itemize} - \item - If \verb@S@ has a base class \verb@D[U$_1$, ..., U$_n$]@, for some type parameters - \verb@[U$_1$, ..., U$_n$]@, then \verb@T@ seen as a member of $C$ from $S$ is $U_i$. - \item - Otherwise, if $C$ is defined in a class $C'$, then - \verb@T@ seen as a member of $C$ from $S$ is the same as $T$ seen as - a member of $C'$ from $S'$. - \item - Otherwise, if $C$ is not defined in another class, then - \verb@T@ seen as a member of $C$ from $S$ is $T$ itself. - \end{itemize} -\item - Otherwise, - if \verb@T@ is the singleton type \verb@D.this.type@ for some class \verb@D@ - then - \begin{itemize} - \item - If \verb@D@ is a subclass of \verb@C@ and - \verb@S@ has a type instance of class $D$ among its base classes. - then \verb@T@ seen as a member of $C$ from $S$ is $S$. - \item - Otherwise, if $C$ is defined in a class $C'$, then - \verb@T@ seen as a member of $C$ from $S$ is the same as $T$ seen as - a member of $C'$ from $S'$. - \item - Otherwise, if $C$ is not defined in another class, then - \verb@T@ seen as a member of $C$ from $S$ is $T$ itself. - \end{itemize} -\item - If $T$ is some other type, then the described mapping is performed - to all its type components. -\end{itemize} - -If \verb@T@ is a possibly parameterized class type, where $T$'s class -is defined in some other class $D$, and \verb@S@ is some prefix type, -then we use ``\verb@T@ seen from \verb@S@'' as a shorthand for -``\verb@T@ seen as a member of $D$ from $S$. - -3. The {\em member bindings} of a type $T$ are all bindings $d$ such that -there exists a type instance of some class $C$ among the base classes of $T$ -and there exists a definition or declaration $d'$ in $C$ -such that $d$ results from $d'$ by replacing every -type $T'$ in $d'$ by $T'$ seen as a member of $C$ from $T$. - -The {\em definition} of a type projection \verb@S#t@ is the member -binding $d$ of the type \verb@t@ in \verb@S@. In that case, we also say -that \verb@S#t@ {\em is defined by} \verb@d@. - -\section{Relations between types} - -We define two relations between types. -\begin{quote}\begin{tabular}{l@{\tab}l@{\tab}l} -\em Type equivalence & $T \equiv U$ & $T$ and $U$ are interchangeable -in all contexts. -\\ -\em Conformance & $T \conforms U$ & Type $T$ conforms to type $U$. -\end{tabular}\end{quote} - -\subsection{Type Equivalence} -\label{sec:type-equiv} - -Equivalence $(\equiv)$ between types is the smallest congruence\footnote{ A -congruence is an equivalence relation which is closed under formation -of contexts} such that the following holds: -\begin{itemize} -\item -If $t$ is defined by a type alias \verb@type t = T@, then $t$ is -equivalent to $T$. -\item -If a path $p$ has a singleton type \verb@q.type@, then -\verb@p.type $\equiv$ q.type@. -\item -If \verb@O@ is defined by an object definition, and \verb@p@ is a path -consisting only of package or object selectors and ending in \verb@O@, then -\verb@O.this.type $\equiv$ p.type@. -\item -Two compound types are equivalent if their component types are -pairwise equivalent and their refinements are equivalent. Two -refinements are equivalent if they bind the same names and the -modifiers, types and bounds of every declared entity are equivalent in -both refinements. -\item -Two method types are equivalent if they have equivalent result -types, both have the same number of parameters, and corresponding -parameters have equivalent types as well as the same \verb@def@ or -\verb@*@ modifiers. Note that the names of parameters do not matter -for method type equivalence. -\item -Two polymorphic types are equivalent if they have the same number of -type parameters, and, after renaming one set of type parameters by -another, the result types as well as lower and upper bounds of -corresponding type parameters are equivalent. -\item -Two overloaded types are equivalent if for every alternative type in -either type there exists an equivalent alternative type in the other. -\end{itemize} - -\subsection{Conformance} -\label{sec:subtyping} - -The conformance relation $(\conforms)$ is the smallest -transitive relation that satisfies the following conditions. -\begin{itemize} -\item Conformance includes equivalence. If $T \equiv U$ then $T \conforms U$. -\item For every value type $T$, \verb@scala.All <: T <: scala.Any@. -\item For every value type \verb@T <: scala.AnyRef@ one has \verb@scala.AllRef <: T@. -\item A type variable or abstract type $t$ conforms to its upper bound and - its lower bound conforms to $t$. -\item A class type or parameterized type $c$ conforms to any of its basetypes, $b$. -\item A type projection \verb@T#t@ conforms to \verb@U#t@ if - \verb@T@ conforms to \verb@U@. -\item A parameterized type \verb@T[T$_1$, ..., T$_n$]@ conforms to - \verb@T[U$_1$, ..., U$_n$]@ if - the following three conditions hold for $i = 1 \commadots n$. - \begin{itemize} - \item - If the $i$'th type parameter of $T$ is declared covariant, then $T_i <: U_i$. - \item - If the $i$'th type parameter of $T$ is declared contravariant, then $U_i <: T_i$. - \item - If the $i$'th type parameter of $T$ is declared neither covariant - nor contravariant, then $U_i \equiv T_i$. - \end{itemize} -\item A compound type \verb@T$_1$ with ... with T$_n$ {R}@ conforms to - each of its component types \verb@T$_i$@. -\item If $T \conforms U_i$ for $i = 1 \commadots n$ and for every - binding of a type or value $x$ in $R$ there exists a member binding of - $x$ in $T$ which is more specific, then $T$ conforms to - the compound type \verb@T$_1$ with ... with T$_n$ {R}@. -\item If - $T'_i$ conforms to $T_i$ for $i = 1 \commadots n$ and $U$ conforms to $U'$ - then the method type $(T_1 \commadots T_n) U$ conforms to - $(T'_1 \commadots T'_n) U'$. -\item If, assuming -$L'_1 \conforms a_1 \conforms U'_1 \commadots L'_n \conforms a_n \conforms U'_n$ -one has $L_i \conforms L'_i$ and $U'_i \conforms U_i$ -for $i = 1 \commadots n$, as well as $T \conforms T'$ then the polymorphic type -$[a_1 >: L_1 <: U_1 \commadots a_n >: L_n <: U_n] T$ conforms to the polymorphic type -$[a_1 >: L'_1 <: U'_1 \commadots a_n >: L'_n <: U'_n] T'$. -\item -An overloaded type $T_1 \overload \ldots \overload T_n$ conforms to each of its alternative types $T_i$. -\item -A type $S$ conforms to the overloaded type $T_1 \overload \ldots \overload T_n$ -if $S$ conforms to each alternative type $T_i$. -\end{itemize} - -A declaration or definition in some compound type of class type $C$ -is {\em more specific} than another -declaration of the same name in some compound type or class type $C'$. -\begin{itemize} -\item -A value declaration \verb@val x: T@ or value definition -\verb@val x: T = e@ is more specific than a value declaration -\verb@val x: T'@ if $T <: T'$. -\item -A type alias -$\TYPE;t=T$ is more specific than a type alias $\TYPE;t=T'$ if -$T \equiv T'$. -\item -A type declaration \verb@type t >: L <: U@ is more specific that -a type declaration \verb@type t >: L' <: U'@ if \verb@L' <: L@ and \verb@U <: U'@. -\item -A type or class definition of some type $t$ is more specific than an abstract -type declaration \verb@type t >: L <: U@ if -\verb@L <: t <: U@. -\end{itemize} - -The \verb@<:@ relation forms a partial order between types. The {\em -least upper bound} or the {\em greatest lower bound} of a set of types -is understood to be relative to that order. - -\section{Type Erasure} -\label{sec:erasure} - -A type is called {\em generic} if it contains type arguments or type variables. -{\em Type erasure} is a mapping from (possibly generic) types to -non-generic types. We write $|T|$ for the erasure of type $T$. -The erasure mapping is defined as follows. -\begin{itemize} -\item The erasure of a type variable is the erasure of its upper bound. -\item The erasure of a parameterized type $T[T_1 \commadots T_n]$ is $|T|$. -\item The erasure of a singleton type \verb@p.type@ is the - erasure of the type of \verb@p@. -\item The erasure of a type projection \verb@T#x@ is \verb@|T|#x@. -\item The erasure of a compound type $T_1;\WITH;\ldots;\WITH;T_n\{R\}$ is $|T_1|$. -\item The erasure of every other type is the type itself. -\end{itemize} - -\section{Implicit Conversions} -\label{sec:impl-conv} - -If $S \conforms T$, then values of type $S$ are implicitly {\em -converted} to values type of $T$ in situations where a value of type -$T$ is required. A conversion between two number types in \verb@int@, -\verb@long@, \verb@float@, \verb@double@ creates a value of the target -type representing the same number as the source. When used in an -expression, a value of type \verb@byte@, \verb@char@, \verb@short@ is -always implicitly converted to a value of type \verb@int@. - -The following implicit conversions are applied to expressions of -method type that are used as values, rather than being applied to some -arguments. -\begin{itemize} -\item -A parameterless method $m$ of type $[] T$ -is converted to type $T$ by evaluating the expression to which $m$ is bound. -\item -An expression $e$ of polymorphic type -\verb@[a$_1$ >: L$_1$ <: U$_1$, ..., a$_n$ >: L$_n$ <: U$_n$]T@ -which does not appear as the function part of -a type application is converted to type \verb@T@ -by determining with local type inference -(\sref{sec:local-type-inf}) instance types \verb@T$_1$, ..., T$_n$@ -for the type variables \verb@a$_1$, ..., a$_n$@ and -implicitly embedding \verb@e@ in the type application -\verb@e[U$_1$, ..., U$_n$]@ (\sref{sec:type-app}). -\item -An expression \verb@e@ of monomorphic method type -$(Ts_1) \ldots (Ts_n) U$ of arity $n > 0$ -which does not appear as the function part of an application is -converted to a function type by implicitly embedding $e$ in -the following term, where $x$ is a fresh variable and each $ps_i$ is a -parameter section consisting of parameters with fresh names of types $Ts_i$. - -\begin{verbatim} -(val $x$ = $e$ ; $(ps_1) \ldots \Arrow \ldots \Arrow (ps_n) \Arrow x;(ps_1);\ldots;(ps_n)$) -\end{verbatim} -This conversion is not applicable to functions with call-by-name -parameters (\sref{sec:parameters}) of type $[]T$, because its result -would violate the well-formedness rules for anonymous functions -(\sref{sec:closures}). Hence, methods with call-by-name -parameters always need to be applied to arguments immediately. -\end{itemize} - -\chapter{Basic Declarations and Definitions} -\label{sec:defs} - -\syntax\begin{verbatim} - Dcl \=::=\= val ValDcl {`,' ValDcl} - \> |\> var VarDcl {`,' VarDcl} - \> |\> def FunDcl {`,' FunDcl} - \> |\> type TypeDcl {`,' TypeDcl} - Def \>::=\> val PatDef {`,' PatDef} - \> |\> var VarDef {`,' VarDef} - \> |\> def FunDef {`,' FunDef} - \> |\> type TypeDef {`,' TypeDef} - \> |\> ClsDef -\end{verbatim} - -A {\em declaration} introduces names and assigns them types. It can -appear as one of the statements of a class definition -(\sref{sec:templates}) or as part of a refinement in a compound -type (\sref{sec:refinements}). - -A {\em definition} introduces names that denote terms or types. It can -form part of an object or class definition or it can be local to a -block. Both declarations and definitions produce {\em bindings} that -associate type names with type definitions or bounds, and that -associate term names with types. - -The scope of a name introduced by a declaration or definition is the -whole statement sequence containing the binding. However, there is a -restriction on forward references: In a statement sequence $s_1 \ldots -s_n$, if a simple name in $s_i$ refers to an entity defined by $s_j$ -where $j \geq i$, then every non-empty statement between and including -$s_i$ and $s_j$ must be an import clause, -or a function, type, class, or object definition. - -\comment{ -Every basic definition may introduce several defined names, separated -by commas. These are expanded according to the following scheme: -\bda{lcl} -\VAL;x, y: T = e && \VAL; x: T = e \\ - && \VAL; y: T = x \\[0.5em] - -\LET;x, y: T = e && \LET; x: T = e \\ - && \VAL; y: T = x \\[0.5em] - -\DEF;x, y (ps): T = e &\tab\mbox{expands to}\tab& \DEF; x(ps): T = e \\ - && \DEF; y(ps): T = x(ps)\\[0.5em] - -\VAR;x, y: T := e && \VAR;x: T := e\\ - && \VAR;y: T := x\\[0.5em] - -\TYPE;t,u = T && \TYPE; t = T\\ - && \TYPE; u = t\\[0.5em] -\eda -} - -All definitions have a ``repeated form'' where the initial -definition keyword is followed by several constituent definitions -which are separated by commas. A repeated definition is -always interpreted as a sequence formed from the -constituent definitions. E.g.\ the function definition -\verb@def f(x) = x, g(y) = y@ expands to -\verb@def f(x) = x; def g(y) = y@ and -the type definition -\verb@type T$_1$, T$_2$ <: B$_2$@ expands to -\verb@type T$_1$; type T$_2$ <: B$_2$@. - -\section{Value Declarations and Definitions} -\label{sec:valdef} - -\syntax\begin{verbatim} - Dcl \=::= \= val ValDcl {`,' ValDcl} - ValDcl \>::= \> id `:' Type - Def \>::= \> val PatDef {`,' PatDef} - PatDef \>::= \> Pattern `=' Expr -\end{verbatim} - -A value declaration \verb@val x: T@ introduces \verb@x@ as a name of a value of -type \verb@T@. - -A value definition \verb@val x: T = e@ defines $x$ as a name of the -value that results from the evaluation of $e$. The type $T$ may be -omitted, in which case the type of expression $e$ is assumed. -If a type $T$ is given, then $e$ is expected to conform to it. - -Evaluation of the value definition implies evaluation of its -right-hand side $e$. The effect of the value definition is to bind -$x$ to the value of $e$ converted to type $T$. - -Value definitions can alternatively have a pattern -(\sref{sec:patterns}) as left-hand side. If $p$ is some pattern other -than a simple name or a name followed by a colon and a type, then the -value definition \verb@val p = e@ is expanded as follows: - -1. If the pattern $p$ has bound variables $x_1 \commadots x_n$, where $n > 1$: -\begin{verbatim} -val $\Dollar$x = e.match {case p => scala.Tuple$\,n$(x$_1$, ..., x$_n$)} -val x$_1$ = $\Dollar$x._1 -... -val x$_n$ = $\Dollar$x._n . -\end{verbatim} -Here, \verb@$\Dollar$x@ is a fresh name. The class -\verb@Tuple$\,n$@ is defined for $n = 2,...,9$ in package -\verb@scala@. - -2. If $p$ has a unique bound variable $x$: -\begin{verbatim} -val x = e.match { case p => x } -\end{verbatim} - -3. If $p$ has no bound variables: -\begin{verbatim} -e.match { case p => ()} -\end{verbatim} - -\example -The following are examples of value definitions -\begin{verbatim} -val pi = 3.1415; -val pi: double = 3.1415; \=// equivalent to first definition -val Some(x) = f(); \>// a pattern definition -val x :: xs = mylist; \>// an infix pattern definition -\end{verbatim} - -The last two definitions have the following expansions. -\begin{verbatim} -val x = f().match { case Some(x) => x } - -val x$\Dollar$ = mylist.match { case x :: xs => scala.Tuple2(x, xs) } -val x = x$\Dollar$._1; -val xs = x$\Dollar$._2; - -\end{verbatim} - -\section{Variable Declarations and Definitions} -\label{sec:vardef} - -\syntax\begin{verbatim} - Dcl \=::= \= var VarDcl {`,' VarDcl} - Def \>::= \> var ValDef {`,' ValDef} - VarDcl \>::=\> id `:' Type - VarDef \>::=\> id [`:' Type] `=' Expr - \> |\> id `:' Type `=' `_' -\end{verbatim} - -A variable declaration \verb@var x: T@ is equivalent to declarations -of a {\em getter function} \verb@x@ and a {\em setter function} -\verb@x_=@, defined as follows: - -\begin{verbatim} - def x: T; - def x_= (y: T): unit -\end{verbatim} - -An implementation of a class containing variable declarations -may define these variables using variable definitions, or it may -define setter and getter functions directly. - -A variable definition \verb@var x: T = e@ introduces a mutable -variable with type \verb@T@ and initial value as given by the -expression \verb@e@. The type $T$ can be omitted, -in which case the type of $e$ is assumed. If $T$ is given, then \verb@e@ -is expected to conform to it. - -A variable definition \verb@var x: T = _@ introduces a mutable -variable with type \verb@T@ and a default initial value. -The default value depends on the type \verb@T@ as follows: -\begin{quote}\begin{tabular}{ll} -\verb@0@ & if $T$ is \verb@int@ or one of its subrange types, \\ -\verb@0L@ & if $T$ is \verb@long@,\\ -\verb@0.0f@ & if $T$ is \verb@float@,\\ -\verb@0.0d@ & if $T$ is \verb@double@,\\ -\verb@false@ & if $T$ is \verb@boolean@,\\ -\verb@()@ & if $T$ is \verb@unit@, \\ -\verb@null@ & for all other types $T$. -\end{tabular}\end{quote} - -When they occur as members of a template, both forms of variable -definition also introduce a getter function \verb@x@ which returns the -value currently assigned to the variable, as well as a setter function -\verb@x_=@ which changes the value currently assigned to the variable. -The functions have the same signatures as for a variable declaration. -The getter and setter functions, are then members of the template -instead of the variable accessed by them. - -\example The following example shows how {\em properties} can be -simulated in Scala. It defines a class \verb@TimeOfDayVar@ of time -values with updatable integer fields representing hours, minutes, and -seconds. Its implementation contains tests that allow only legal -values to be assigned to these fields. The user code, on the other -hand, accesses these fields just like normal variables. - -\begin{verbatim} -class TimeOfDayVar { - private var h: int = 0, m: int = 0, s: int = 0; - def hours \== h; - def hours_= (h: int) \>= \=if (0 <= h && h < 24) this.h = h - \> \>else new DateError().throw; - def minutes \>= m - def minutes_= (m: int) \>= if (0 <= m && m < 60) this.m = m - \> \>else new DateError().throw; - def seconds \>= s - def seconds_= (s: int) \>= if (0 <= s && s < 60) this.s = s - \> \>else new DateError().throw; -} -val t = new TimeOfDayVar; -d.hours = 8; d.minutes = 30; d.seconds = 0; -d.hours = 25; \=// throws a DateError exception -\end{verbatim} - -\section{Type Declarations and Type Aliases} -\label{sec:typedcl} -\label{sec:typealias} - -\syntax\begin{verbatim} - Dcl \=::= \= type TypeDcl {`,' TypeDcl} - TypeDcl \>::= \> id [>: Type] [<: Type] - Def \>::= \> type TypeDef {`,' TypeDef} - TypeDef \>::= \> id [TypeParamClause] `=' Type -\end{verbatim} - -A {\em type declaration} \verb@type t >: L <: U@ declares \verb@t@ to -be an abstract type with lower bound type \verb@L@ and upper bound -type \verb@U@. If such a declaration appears as a member declaration -of a type, implementations of the type may implement \verb@t@ with any -type \verb@T@ for which \verb@L <: T <: U@. Either or both bounds may -be omitted. If the lower bound \verb@L@ is missing, the bottom type -\verb@scala.All@ is assumed. If the upper bound \verb@U@ is missing, -the top type \verb@scala.Any@ is assumed. - -A {\em type alias} \verb@type t = T@ defines \verb@t@ to be an alias -name for the type \verb@T@. The left hand side of a type alias may -have a type parameter clause, e.g. \verb@type t[tps] = T@. The scope -of a type parameter extends over the right hand side \verb@T@ and the -type parameter clause \verb@tps@ itself. - -The scope rules for definitions (\sref{sec:defs}) and type parameters -(\sref{sec:funsigs}) make it possible that a type name appears in its -own bound or in its right-hand side. However, it is a static error if -a type alias refers recursively to the defined type constructor itself. -That is, the type \verb@T@ in a type alias \verb@type t[tps] = T@ may not refer -directly or indirectly to the name \verb@t@. It is also an error if -an abstract type is directly or indirectly its own bound. - -\example The following are legal type declarations and definitions: -\begin{verbatim} -type IntList = List[Integer]; -type T <: Comparable[T]; -type Two[a] = Tuple2[a, a]; -\end{verbatim} - -The following are illegal: -\begin{verbatim} -type Abs = Comparable[Abs]; \=// recursive type alias - -type S <: T; \>// S, T are bounded by themselves. -type T <: S; - -type T <: Object with T; \>// T is abstract, may not be part of - \>// compound type - -type T >: Comparable[T.That]; \>// Cannot select from T. - \>// T is a type, not a value -\end{verbatim} - -If a type alias \verb@type t[tps] = S@ refers to a class type -\verb@S@, the name \verb@t@ can also be used as a constructor for -objects of type \verb@S@. - -\example The \verb@Predef@ module contains a definition which establishes \verb@Pair@ -as an alias of the parameterized class \verb@Tuple2@: -\begin{verbatim} -type Pair[+a, +b] = Tuple2[a, b]; -\end{verbatim} -As a consequence, for any two types \verb@S@ and \verb@T@, the type -\verb@Pair[S, T]@ is equivalent to the type \verb@Tuple2[S, T]@. -\verb@Pair@ can also be used as a constructor instead of \verb@Tuple2@, as in -\begin{verbatim} -new Pair[Int, Int](1, 2) . -\end{verbatim} - -\section{Type Parameters} - -\syntax\begin{verbatim} - TypeParamClause \=::=\= `[' TypeParam {`,' TypeParam} `]' - TypeParam \>::=\> [`+' | `-'] TypeDcl -\end{verbatim} - -\newcommand{\plusminus}{\oplus} - -Type parameters appear in type definitions, class definitions, and -function definitions. The most general form of a type parameter is -\verb@$\plusminus$ t >: L <: U@. Here, \verb@L@, and \verb@U@ are lower -and upper bounds that constrain possible type arguments for the -parameter. $\plusminus$ is a {\em variance}, i.e.\ an optional prefix -of either \verb@+@, or \verb@-@. - -The names of all type parameters in a type parameter clause must be -pairwise different. The scope of a type parameter includes in each -case the whole type parameter clause. Therefore it is possible that a -type parameter appears as part of its own bounds or the bounds of -other type parameters in the same clause. However, a type parameter -may not be bounded directly or indirectly by itself. - -\example Here are some well-formed type parameter clauses: -\begin{verbatim} -[s, t] -[ex <: Throwable] -[a <: Ord[b], b <: a] -[a, b, c >: a <: b] -\end{verbatim} -The following type parameter clauses since some type parameter is bounded by itself. -\begin{verbatim} -[a >: a] -[a <: b, b <: c, c <: a] -\end{verbatim} - -Variance annotations indicate how type instances with the given type -parameters vary with respect to subtyping (\sref{sec:subtyping}). A -`\verb@+@' variance indicates a covariant dependency, a `\verb@-@' -variance indicates a contravariant dependency, and a missing variance -indication indicates an invariant dependency. - -A variance annotation constrains the way the annotated type variable -may appear in the type or class which binds the type parameter. In a -type definition \verb@type t[tps] = S@, type parameters labeled -`\verb@+@' must only appear in covariant position in \verb@S@ whereas -type parameters labeled `\verb@-@' must only appear in contravariant -position. Analogously, for a class definition -\verb@class c[tps](ps): s extends t@, type parameters labeled -`\verb@+@' must only appear in covariant position in the self type -\verb@s@ and the type of the template \verb@t@, whereas type -parameters labeled `\verb@-@' must only appear in contravariant -position. - -The variance position of a type parameter of a type is defined as -follows. Let the opposite of covariance be contravariance, and the -opposite of invariance be itself. The top-level of a type is always -in covariant position. The variance position changes at the following -constructs. -\begin{itemize} -\item -The variance position of method parameter is the opposite of the -variance position of the enclosing parameter clause. -\item -The variance position of a type parameter is the opposite of the -variance position of the enclosing type parameter clause. -\item -The variance position of the lower bound of a type declaration or type parameter -is the opposite of the variance position of the type declaration or parameter. -\item -The right hand side \verb@S@ of a type alias \verb@type t[tps] = S@ -is always in invariant position. -\item -The type of a mutable variable is always in invariant position. -\item -The prefix \verb@S@ of a type selection \verb@S#T@ is always in invariant position. -\item -For a type argument \verb@T@ of a type \verb@S[... T ... ]@: If the -corresponding type parameter is invariant, then \verb@T@ is in -invariant position. If the corresponding type parameter is -contravariant, the variance position of \verb@T@ is the opposite of -the variance position of the enclosing type \verb@S[... T ... ]@. -\end{itemize} - -\example The following variance annotation is legal. -\begin{verbatim} -class P[a, b] { - val fst: a, snd: b -}\end{verbatim} -With this variance annotation, elements -of type \verb@P@ subtype covariantly with respect to their arguments. -For instance, \verb@P[IOExeption, String] <: P[Throwable, Object]@. - -If we make the elements of \verb@P@ mutable, -the variance annotation becomes illegal. -\begin{verbatim} -class Q[+a, +b] { - var fst: a, snd: b // **** error: illegal variance: `a', `b' occur in invariant position. -} -\end{verbatim} - -\example The following variance annotation is illegal, since \verb@a@ appears -in contravariant position in the parameter of \verb@append@: - -\begin{verbatim} -trait Vector[+a] { - def append(x: Vector[a]): Vector[a]; // **** error: illegal variance: `a' occurs in contravariant position. -} -\end{verbatim} -The problem can be avoided by generalizing the type of \verb@append@ -by means of a lower bound: - -\begin{verbatim} -trait Vector[+a] { - def append[b >: a](x: Vector[b]): Vector[b]; -} -\end{verbatim} - -\example Here is a case where a contravariant type parameter is useful. - -\begin{verbatim} -trait OutputChannel[-a] { - def write(x: a): unit -} -\end{verbatim} -With that annotation, we have -\verb@OutputChannel[Object] <: OutputChannel[String]@. That is, a -channel on which one can write any object can substitute for a channel -on which one can write only strings. - -\section{Function Declarations and Definitions} -\label{sec:defdef} -\label{sec:funsigs} - -\syntax\begin{verbatim} -Dcl \=::= \= def FunDcl {`,' FunDcl} -FunDcl \>::= \> id [FunTypeParamClause] {ParamClause} `:' Type -Def \>::= \> def FunDef {`,' FunDef} -FunDef \>::= \> id [FunTypeParamClause] {ParamClause} [`:' Type] - \> \> `=' Expr -FunTypeParamClause \>::=\> `[' TypeDcl {`,' TypeDcl} `]' -ParamClause \>::=\> `(' [Param {`,' Param}] `)' -Param \>::= \> [def] id `:' Type [*] -\end{verbatim} - -A function declaration has the form \verb@def f psig: T@, where -\verb@f@ is the function's name, \verb@psig@ is its parameter -signature and \verb@T@ is its result type. A function definition -\verb@f psig:T = e@ also includes a {\em function body} \verb@e@, -i.e.\ an expression which defines the function's result. A parameter -signature consists of an optional type parameter clause \verb@[tps]@, -followed by zero or more value parameter clauses -\verb@(ps$_1$) ... (ps$_n$)@. Such a declaration or definition -introduces a value with a (possibly polymorphic) method type whose -parameter types and result type are as given. - -A type parameter clause \verb@tps@ consists of one or more type -declarations (\sref{sec:typedcl}), which introduce type parameters, -possibly with bounds. The scope of a type parameter includes -the whole signature, including any of the type parameter bounds as -well as the function body, if it is present. - -A value parameter clause \verb@ps@ consists of zero or more formal -parameter bindings such as \verb@x: T@, which bind value -parameters and associate them with their types. The scope of a formal -value parameter name \verb@x@ is the function body, if one is -given. Both type parameter names and value parameter names must be -pairwise distinct. - -Value parameters may be prefixed by \verb@def@, e.g.\ -\verb@def x:T@. The type of such a parameter is then the -parameterless method type \verb@[]T@. This indicates that the -corresponding argument is not evaluated at the point of function -application, but instead is evaluated at each use within the -function. That is, the argument is evaluated using {\em call-by-name}. - -\example The declaration -\begin{verbatim} -def whileLoop (def cond: Boolean) (def stat: Unit): Unit -\end{verbatim} -produces the typing -\begin{verbatim} -whileLoop: (cond: [] Boolean) (stat: [] Unit) Unit -\end{verbatim} -which indicates that both parameters of \verb@while@ are evaluated using -call-by-name. - -The type of the function body must conform to the function's declared -result type, if one is given. If the function definition is not -recursive, the result type may be omitted, in which case it is -determined from the type of the function body. - -\section{Overloaded Definitions} -\label{sec:overloaded-defs} -\todo{change} - -An overloaded definition is a set of \verb@n > 1@ value or function -definitions in the same statement sequence that define the same name, -binding it to types \verb@T_1, ..., T_n@, respectively. The -individual definitions are called {\em alternatives}. Alternatives -always need to specify the type of the defined entity completely. All -alternatives must have the same modifiers. It is an error if the types -of two alternatives \verb@T$_i$@ and \verb@T$_j$@ have the same -erasure (\sref{sec:erasure}). An overloaded definition defines a -single entity, of type \verb@T_1 $\overload$ ... $\overload$ T_n@ -(\sref{sec:overloaded-types}). - -\todo{Say something about bridge methods.} -%This must be a well-formed -%overloaded type - -\section{Import Clauses} -\label{sec:import} - -\syntax\begin{verbatim} - Import \=::=\= import ImportExpr {`,' ImportExpr} - ImportExpr \>::=\> StableId `.' (id | `_' | ImportSelectors) - ImportSelectors \>::=\> `{' {ImportSelector `,'} (ImportSelector | `_') `}' - ImportSelector \>::=\> id [`=>' id | `=>' `_'] -\end{verbatim} - -An import clause has the form \verb@import p.I@ where \verb@p@ is a stable -identifier (\sref{sec:paths}) and \verb@I@ is an import expression. -The import expression determines a set of names of members of \verb@p@ -which are made available without qualification. The most general form -of an import expression is a list of {\em import selectors} -\begin{verbatim} -{ x$_1$ => y$_1$, ..., x$_n$ => y$_n$, _ } -\end{verbatim} -for $n \geq 0$, where the final wildcard `\verb@_@' may be absent. It -makes available each member \verb@p.x$_i$@ under the unqualified name -\verb@y$_i$@. I.e.\ every import selector \verb@x$_i$ => y$_i$@ renames -\verb@p.x$_i$@ to -\verb@y$_i$@. If a final wildcard is present, all members \verb@z@ of -\verb@p@ other than \verb@x$_1$, ..., x$_n$@ are also made available -under their own unqualified names. - -Import selectors work in the same way for type and term members. For -instance, an import clause \verb@import p.{x => y}@ renames the term -name \verb@p.x@ to the term name \verb@y@ and the type name \verb@p.x@ -to the type name \verb@y@. At least one of these two names must -reference a member of \verb@p@. - -If the target in an import selector is a wildcard, the import selector -hides access to the source member. For instance, the import selector -\verb@x => _@ ``renames'' \verb@x@ to the wildcard symbol (which is -unaccessible as a name in user programs), and thereby effectively -prevents unqualified access to \verb@x@. This is useful if there is a -final wildcard in the same import selector list, which imports all -members not mentioned in previous import selectors. - -Several shorthands exist. An import selector may be just a simple name -\verb@x@. In this case, \verb@x@ is imported without renaming, so the -import selector is equivalent to \verb@x => x@. Furthermore, it is -possible to replace the whole import selector list by a single -identifier or wildcard. The import clause \verb@import p.x@ is -equivalent to \verb@import p.{x}@, i.e.\ it makes available without -qualification the member \verb@x@ of \verb@p@. The import clause -\verb@import p._@ is equivalent to -\verb@import p.{_}@, -i.e.\ it makes available without qualification all members of \verb@p@ -(this is analogous to \verb@import p.*@ in Java). - -An import clause with multiple import expressions -\verb@import p$_1$.I$_1$, ..., p$_n$.I$_n$@ is interpreted as a -sequence of import clauses -\verb@import p$_1$.I$_1$; ..., import p$_n$.I$_n$@. - -\example Consider the object definition: -\begin{verbatim} -object M { - def z = 0, one = 1; - def add(x: Int, y: Int): Int = x + y -} -\end{verbatim} -Then the block -\begin{verbatim} -{ import M.{one, z => zero, _}; add(zero, one) } -\end{verbatim} -is equivalent to the block -\begin{verbatim} -{ M.add(M.z, M.one) } . -\end{verbatim} - -\chapter{Classes and Objects} -\label{sec:globaldefs} - -\syntax\begin{verbatim} - ClsDef \=::=\= ([case] class | trait) ClassDef {`,' ClassDef} - \> |\> [case] object ObjectDef {`,' ObjectDef} -\end{verbatim} - -Classes (\sref{sec:classes}) and objects -(\sref{sec:modules}) are both defined in terms of {\em templates}. - -\section{Templates} -\label{sec:templates} - -\syntax\begin{verbatim} - Template \=::=\= Constr {`with' Constr} [TemplateBody] - TemplateBody \>::=\> `{' [TemplateStat {`;' TemplateStat}] `}' -\end{verbatim} - -A template defines the type signature, behavior and initial state of a -class of objects or of a single object. Templates form part of -instance creation expressions, class definitions, and object -definitions. A template -\verb@sc with mc$_1$ with ... with mc$_n$ {stats}@ consists of a -constructor invocation \verb@sc@ which defines the template's {\em -superclass}, constructor invocations \verb@mc$_1$, ..., mc$_n$@ -$(n \geq 0)$, which define the template's {\em mixin classes}, and a -statement sequence \verb@stats@ which contains additional member -definitions for the template. Superclass and mixin classes together -are called the {\em parent classes} of a template. The superclass of -a template must be a subtype of the superclass of each mixin class. -The {\em least proper supertype} of a template is the class type or -compound type (\sref{sec:compound-types}) consisting of the its parent classes. - -Member definitions define new members or overwrite members in the -parent classes. If the template forms part of a class definition, -the statement part \verb@stats@ may also contain declarations of abstract members. -%The type of each non-private definition or declaration of a -%template must be equivalent to a type which does not refer to any -%private members of that template. - -\todo{Make all references to Java generic} - -\paragraph{Inheriting from Java Types} A template may have a Java class as -its superclass and Java interfaces as its mixin classes. On the other -hand, it is not permitted to have a Java class as a mixin class, or a -Java interface as a superclass. - -\subsection{Constructor Invocations} -\label{sec:constr-invoke} -\syntax\begin{verbatim} - Constr \=::= \= StableId [TypeArgs] [`(' [Exprs] `)'] -\end{verbatim} - -Constructor invocations define the type, members, and initial state of -objects created by an instance creation expression, or of parts of an -object's definition which are inherited by a class or object -definition. A constructor invocation is a function application -\verb@x.c(args)@, where \verb@x@ is a stable identifier -(\sref{sec:stable-ids}), \verb@c@ is a type name which either -designates a class or defines an alias type for one, and \verb@(args)@ -is an argument list, which matches one of the constructors of that -class. The prefix `\verb@x.@' can be omitted. -%The class \verb@c@ must conform to \verb@scala.AnyRef@, -%i.e.\ it may not be a value type. -The argument list \verb@(args)@ can also be omitted, in which case an -empty argument list \verb@()@ is implicitly added. - -\subsection{Base Classes} -\label{sec:base-classes} - -For every template, class type and constructor invocation we define two -sequences of class types: the {\em base classes} and {\em mixin base -classes}. Their definitions are as follows. - -The {\em mixin base classes} of a template -\verb@sc with mc$_1$ with ... with mc$_n$ {stats}@ are obtained by -concatenating, for each $i = 1 \commadots n$, the mixin base classes -of the mixin \verb@mc_i@. The mixin base classes of a class type \verb@C@ are -the mixin base classes of the template represented by \verb@C@, followed by -\verb@C@ itself. The mixin base classes of a constructor invocation of type -\verb@T@ are the mixin base classes of class \verb@T@. - -The {\em base classes} of a template consist of the base classes of -its superclass, followed by the template's mixin base classes. The -base classes of class \verb@scala.Any@ consist of just the -class itself. The base classes of some other class type \verb@C@ are the -base classes of the template represented by \verb@C@, followed by \verb@C@ -itself. The base classes of a constructor invocation of type \verb@T@ -are the base classes of \verb@T@. - -The notions of mixin base classes and base classes are extended from -classes to arbitrary types following the definitions of -\sref{sec:base-classes}. - -If two types in the base class sequence of a template refer to the -same class definition, then that definition must define a trait -(\sref{sec:traits}), and the type that comes later in the sequence must -conform to the type that comes first. -(\sref{sec:case-classes}). - -\subsection{Evaluation} - -The evaluation of a template or constructor invocation depends on -whether the template defines an object or is a superclass of a -constructed object, or whether it is used as a mixin for a defined -object. In the second case, the evaluation of a template used as a -mixin depends on an {\em actual superclass}, which is known at the -point where the template is used in a definition of an object, but not -at the point where it is defined. The actual superclass is used in the -determination of the meaning of \verb@super@ (\sref{sec:this-super}). - -We therefore define two notions of template evaluation: (Plain) -evaluation (as a defining template or superclass) and mixin evaluation -with a given superclass \verb@sc@. These notions are defined for templates -and constructor invocations as follows. - -A {\em mixin evaluation with superclass \verb@sc@} of a template -\verb@sc' with mc$_1$ with mc$_n$ with {stats}@ consists of mixin -evaluations with superclass \verb@sc@ of the mixin constructor invocations -\verb@mc$_1$, ..., mc$_n$@ in the order they are given, followed by an -evaluation of the statement sequence \verb@stats@. Within \verb@stats@ the -actual superclass refers to \verb@sc@. A mixin evaluation with superclass -\verb@sc@ of a class constructor invocation \verb@ci@ consists of an evaluation -of the constructor function and its arguments in the order they are -given, followed by a mixin evaluation with superclass \verb@sc@ of the -template represented by the constructor invocation. - -An {\em evaluation} of a template -\verb@sc with mc$_1$ with mc$_n$ with (stats)@ consists of an evaluation of -the superclass constructor invocation \verb@sc@, -followed by a mixin evaluation with superclass \verb@sc@ of the template. An -evaluation of a class constructor invocation \verb@ci@ consists of an -evaluation of the constructor function and its arguments in -the order they are given, followed by an evaluation of the template -represented by the constructor invocation. - -\subsection{Template Members} - -\label{sec:members} - -The object resulting from evaluation of a template has directly bound -members and inherited members. Members can be abstract or concrete. -These are defined as follows. -\begin{enumerate} -\item -A {\em directly bound} member is an entity introduced by a member -definition or declaration in the template's statement sequence. The -member is called {\em abstract} if it is introduced by a declaration, -{\em concrete} otherwise. -\item -A {\em concrete inherited} member is a non-private, concrete member of -one of the template's base classes \verb@B@, except if a member with the -same \ifqualified{qualified} name is already directly bound in the template, or is -directly bound in a base class of the template which is a subclass of -\verb@B@, or is a directly bound, non-private, concrete member of a base -class which succeeds \verb@B@ in the base class sequence of the template. -\item -An {\em abstract inherited} member is a non-private, abstract member -of one of the template's base classes \verb@B@, except if a member with the -same \ifqualified{qualified} name is already directly bound in the template, or is a -concrete inherited member, or is a directly bound, non-private member -of a base class which succeeds \verb@b@ in the base class sequence of the -template. -\end{enumerate} - -If two mixin classes of a template each have a concrete member -with the same name, then the template itself must also declare or -define a member with the same name. - -\comment{ -The type of a member \verb@m@ is determined as follows: If \verb@m@ is defined -in \verb@stats@, then its type is the type as given in the member's -declaration or definition. Otherwise, if \verb@m@ is inherited from the -base class \verb@B[T1, .... T_n]@, \verb@B@'s class declaration has formal -parameters \verb@[a_1, ..., a_n]@, and \verb@M@'s type in \verb@B@ is \verb@U@, then -\verb@M@'s type in \verb@C@ is \verb@U[a_1 := T_1, ..., a_n := T_n]@. - -\ifqualified{ -Members of templates have internally qualified names $Q\qex x$ where -$x$ is a simple name and $Q$ is either the empty name $\epsilon$, or -is a qualified name referencing the module or class that first -introduces the member. A basic declaration or definition of $x$ in a -module or class $M$ introduces a member with the following qualified -name: -\begin{enumerate} -\item -If the binding is labeled with an \verb@override $Q$@\nyi{Override - with qualifier} modifier, -where $Q$ is a fully qualified name of a base class of $M$, then the -qualified name is the qualified expansion (\sref{sec:names}) of $x$ in -$Q$. -\item -If the binding is labeled with an \verb@override@ modifier without a -base class name, then the qualified name is the qualified expansion -of $x$ in $M$'s least proper supertype (\sref{sec:templates}). -\item -An implicit \verb@override@ modifier is added and case (2) also -applies if $M$'s least proper supertype contains an abstract member -with simple name $x$. -\item -If no \verb@override@ modifier is given or implied, then if $M$ is -labeled \verb@qualified@, the qualified name is $M\qex x$. If $M$ is -not labeled \verb@qualified@, the qualified name is $\epsilon\qex x$. -\end{enumerate} -} -} - -\example Consider the class definitions - -\begin{verbatim} -class A { def f: Int = 1 ; def g: Int = 2 ; def h: Int = 3 } -abstract class B { def f: Int = 4 ; def g: Int } -abstract class C extends A with B { def h: Int } -\end{verbatim} - -Then class \verb@C@ has a directly bound abstract member \verb@h@. It -inherits member \verb@f@ from class \verb@B@ and member \verb@g@ from -class \verb@A@. - -\ifqualified{ -\example\label{ex:compound-b} -Consider the definitions: -\begin{verbatim} -qualified class Root extends Any with { def r1: Root, r2: Int } -qualified class A extends Root with { def r1: A, a: String } -qualified class B extends A with { def r1: B, b: Double } -\end{verbatim} -Then \verb@A with B@ has members -\verb@Root::r1@ of type \verb@B@, \verb@Root::r2@ of type \verb@Int@, -\verb@A::a:@ of type \verb@String@, and \verb@B::b@ of type \verb@Double@, -in addition to the members inherited from class \verb@Any@. -} - -\subsection{Overriding} -\label{sec:overriding} - -A template member \verb@M@ that has the same \ifqualified{qualified} -name as a non-private member \verb@M'@ of a base class (and that -belongs to the same namespace) is said to {\em override} that member. -In this case the binding of the overriding member \verb@M@ must be -more specific (\sref{sec:subtyping}) than the binding of the -overridden member \verb@M'@. Furthermore, the overridden definition -may not be a class definition. Method definitions may only override -other method definitions (or the methods implicitly defined by a -variable definition). They may not override value let definitions. -Finally, the following restrictions on modifiers apply to \verb@M@ and -\verb@M'@: -\begin{itemize} -\item -\verb@M'@ must not be labeled \verb@final@. -\item -\verb@M@ must not be labeled \verb@private@. -\item -If \verb@M@ is labeled \verb@protected@, then \verb@M'@ must also be -labeled \verb@protected@. -\item -If \verb@M'@ is not an abstract member, then -\verb@M@ must be labeled \verb@override@. -\end{itemize} - -\example\label{ex:compound-a} -Consider the definitions: -\begin{verbatim} -trait Root with { type T <: Root } -trait A extends Root with { type T <: A } -trait B extends Root with { type T <: B } -trait C extends A with B; -\end{verbatim} -Then the trait definition \verb@C@ is not well-formed because the -binding of \verb@T@ in \verb@C@ is -\verb@type T extends B@, -which fails to be more specific than the binding of same name in type -\verb@A@. The problem can be solved by adding an overriding -definition of type \verb@T@ in class \verb@C@: -\begin{verbatim} -class C extends A with B { type T <: C } -\end{verbatim} - -\subsection{Modifiers} -\label{sec:modifiers} - -\syntax\begin{verbatim} - Modifier \=::=\= LocalModifier - \> |\> private - \> |\> protected - \> |\> override - LocalModifier \>::=\> abstract - \> |\> final - \> |\> sealed -\end{verbatim} - -Member definitions may be preceded by modifiers which affect the -\ifqualified{qualified names, }accessibility and usage of the -identifiers bound by them. If several modifiers are given, their -order does not matter, but the same modifier may not occur repeatedly. -Modifiers preceding a repeated definition apply to all constituent -definitions. The rules governing the validity and meaning of a -modifier are as follows. -\begin{itemize} -\item -The \verb@private@ modifier can be used with any definition in a -template. Private members can be accessed only from within the template -that defines them. -%Furthermore, accesses are not permitted in -%packagings (\sref{sec:topdefs}) other than the one containing the -%definition. -Private members are not inherited by subclasses and they -may not override definitions in parent classes. -\verb@private@ may not be applied to abstract members, and it -may not be combined in one modifier list with -\verb@protected@, \verb@final@ or \verb@override@. -\item -The \verb@protected@ modifier applies to class member definitions. -Protected members can be accessed from within the template of the defining -class as well as in all templates that have the defining class as a base class. -%Furthermore, accesses from the template of the defining class are not -%permitted in packagings other than the one -%containing the definition. -A protected identifier \verb@x@ may be used as -a member name in a selection \verb@r.x@ only if \verb@r@ is one of the reserved -words \verb@this@ and -\verb@super@, or if \verb@r@'s type conforms to a type-instance of the class -which contains the access. -\item -The \verb@override@ modifier applies to class member definitions. It -is mandatory for member definitions that override some other -non-abstract member definition in a super- or mixin-class. If an -\verb@override@ modifier is given, there must be at least one -overridden member definition. Furthermore, the overridden definition -must be concrete (\sref{sec:members}), unless the class containing the -overriding member is abstract. -\item -The \verb@abstract@ modifier is used in class definitions. It is -mandatory if the class has abstract members, or if the class has -members labeled \verb@override@ which override only abstract members -in a parent class. Classes with \verb@abstract@ members -cannot be instantiated (\sref{sec:inst-creation}) with a constructor -invocation unless followed by mixin constructors or statements which -override all abstract members of the class. -\item -The \verb@final@ modifier applies to class member definitions and to -class definitions. A \verb@final@ class member definition may not be -overridden in subclasses. A \verb@final@ class may not be inherited by -a template. \verb@final@ is redundant for object definitions. Members -of final classes or objects are implicitly also final, so the -\verb@final@ modifier is redundant for them, too. \verb@final@ may -not be applied to abstract members, and it may not be combined in one -modifier list with \verb@private@ or \verb@sealed@. -\item -The \verb@sealed@ modifier applies to class definitions. A -\verb@sealed@ class may not be inherited, except if either -\begin{itemize} -\item -the inheriting template is nested within the definition of the sealed -class itself, or -\item -the inheriting template belongs to a class or object definition which -forms part of the same statement sequence as the definition of the -sealed class. -\end{itemize} -\end{itemize} - -\example A useful idiom to prevent clients of a class from -constructing new instances of that class is to declare the class -\verb@abstract@ and \verb@sealed@: - -\begin{verbatim} -object m { - abstract sealed class C (x: Int) { - def nextC = C(x + 1) with {} - } - val empty = new C(0) {} -} -\end{verbatim} -For instance, in the code above clients can create instances of class -\verb@m.C@ only by calling the \verb@nextC@ method of an existing \verb@m.C@ -object; it is not possible for clients to create objects of class -\verb@m.C@ directly. Indeed the following two lines are both in error: - -\begin{verbatim} - m.C(0) \=// **** error: C is abstract, so it cannot be instantiated. - m.C(0) {} \>// **** error: illegal inheritance from sealed class. -\end{verbatim} - -\section{Class Definitions} -\label{sec:classes} - -\syntax\begin{verbatim} - ClsDef \=::=\= class ClassDef {`,' ClassDef} - ClassDef \>::=\> id [TypeParamClause] [ParamClause] [`:' SimpleType] - \> \> ClassTemplate - ClassTemplate \>::=\> extends Template - \> |\> TemplateBody - \> |\> -\end{verbatim} - -The most general form of class definition is -\verb@class c[tps](ps): s extends t@. -Here, -\begin{itemize} -\item[] -\verb@c@ is the name of the class to be defined. -\item[] \verb@tps@ is a non-empty list of type parameters of the class -being defined. The scope of a type parameter is the whole class -definition including the type parameter section itself. It is -illegal to define two type parameters with the same name. The type -parameter section \verb@[tps]@ may be omitted. A class with a type -parameter section is called {\em polymorphic}, otherwise it is called -{\em monomorphic}. -\item[] -\verb@ps@ is a formal parameter clause for the {\em primary -constructor} of the class. The scope of a formal parameter includes -the template \verb@t@. However, the formal parameter may not form -part of the types of any of the parent classes or members of \verb@t@. -It is illegal to define two formal parameters with the same name. -The formal parameter section \verb@(ps)@ may be omitted in which case -an empty parameter section \verb@()@ is assumed. -\item[] -\verb@s@ is the {\em self type} of the class. Inside the -class, the type of \verb@this@ is assumed to be \verb@s@. The self -type must conform to the self types of all classes which are inherited -by the template \verb@t@. The self type declaration `\verb@: s@' may be -omitted, in which case the self type of the class is assumed to be -equal to \verb@c[tps]@. -\item[] -\verb@t@ is a -template (\sref{sec:templates}) of the form -\verb@sc with mc$_1$ with ... with mc$_n$ { stats }@ -which defines the base classes, behavior and initial state of objects of -the class. The extends clause \verb@extends sc with ... with mc$_n$@ -can be omitted, in which case -\verb@extends scala.Object@ is assumed. The class body -\verb@{stats}@ may also be omitted, in which case the empty body -\verb@{}@ is assumed. -\end{itemize} -This class definition defines a type \verb@c[tps]@ and a constructor -which when applied to parameters conforming to types \verb@ps@ -initializes instances of type \verb@c[tps]@ by evaluating the template -\verb@t@. - -\subsection{Constructor Definitions} - -\syntax\begin{verbatim} - FunDef \=::=\= this ParamClause `=' ConstrExpr - ConstrExpr \>::=\> this ArgumentExpr - \> |\> `{' {BlockStat `;'} ConstrExpr `}' -\end{verbatim} - -A class may have additional constructors besides the primary -constructor. These are defined by constructor definitions of the form -\verb@def this(ps) = e@. Such a definition introduces an additional -constructor for the enclosing class, with parameters as given in the -formal parameter list \verb@ps@, and whose evaluation is defined by -the constructor expression \verb@e@. The scope of each formal -parameter is the constructor expression \verb@e@. A constructor -expression is either a self constructor invocation \verb@this(args)@ -or a block which ends in a constructor expression. In terms of -visibility rules, constructor definitions are conceptually outside -their enclosing class. Hence, they can access neither value -parameters nor members of the enclosing class by simple name, and the -value \verb@this@ refers to an object of the class enclosing the class -of the object being constructed. However, constructor definitions can -access type parameters of the enclosing class. - -If there are auxiliary constructors of a class \verb@C@, they define -together with \verb@C@'s primary constructor an overloaded constructor -value. The usual rules for overloading resolution -(\sref{sec:overloaded-defs}) apply for constructor invocations of \verb@C@, -including the self constructor invocations in the constructor -expressions themselves. To prevent infinite cycles of constructor -invocations, there is the restriction that every self constructor -invocation must refer to a constructor definition which precedes it -(i.e. it must refer to either a preceding auxiliary constructor or the -primary constructor of the class). The type of a constructor -expression must be always so that a generic instance of the class is -constructed. I.e., if the class in question has name \verb@C@ and type -parameters \verb@[tps]@, then each constructor must construct an -instance of \verb@C[tps]@; it is not permitted to instantiate formal -type parameters. - -\example Consider the class definition - -\begin{verbatim} -class LinkedList[a <: AnyRef](x: a, xs: LinkedList[a]) { - var head = x; - var tail = xs; - def isEmpty = tail != null; - def this() = this(null, null); - def this(x: a) = { val empty = new LinkedList(); this(x, empty) } -} -\end{verbatim} -This defines a class \verb@LinkedList@ with an overloaded constructor of type -\begin{verbatim} -[a <: AnyRef](x: a, xs: LinkList[a]): LinkedList[a] $\overload$ -[a <: AnyRef](): LinkedList[a] $\overload$ -[a <: AnyRef](x: a): LinkedList[a] . -\end{verbatim} -The second constructor alternative constructs an empty list, while the -third one constructs a list with one element. - -\subsection{Case Classes} -\label{sec:case-classes} - -\syntax\begin{verbatim} ClsDef \=::=\= case class ClassDef {`,' ClassDef} -\end{verbatim} - -If a class definition is prefixed with \verb@case@, the class is said -to be a {\em case class}. The primary constructor of a case class may -be used in a constructor pattern (\sref{sec:patterns}). That -constructor may not have any value parameters which are prefixed by -\verb@def@. None of the base classes of a case class may be a case -class. Furthermore, no type may have two different case classes among -its base types. - -A case class definition of \verb@c[tps](ps)@ with type -parameters \verb@tps@ and value parameters \verb@ps@ implicitly -generates a function definition for a {\em case class factory} -together with the class definition itself: -\begin{verbatim} -def c[tps](ps): s = new c[tps](ps) -\end{verbatim} -(Here, \verb@s@ s the self type of class \verb@c@. -If a type parameter section -is missing in the class, it is also missing in the factory -definition). - -Also implicitly defined are accessor member definitions -in the class that return its value parameters. Every binding -\verb@x: T@ in the parameter section leads to a value definition of -\verb@x@ that defines \verb@x@ to be an alias of the parameter. -%Every -%parameterless function binding \verb@def x: T@ leads to a -%parameterless function definition of \verb@x@ which returns the result -%of invoking the parameter function. -%The case class may not contain a -%directly bound member with the same simple name as one of its value -%parameters. - -Every case class implicitly overrides some method definitions of class -\verb@scala.Object@ (\sref{sec:cls-object}) unless a definition of the same -method is already given in the case class itself or a non-abstract -definition of the same method is given in some base class of the case -class different from \verb@Object@. In particular: -\begin{itemize} -\item[] Method \verb@equals: (Any)boolean@ is structural equality, where two -instances are equal if they belong to the same class and -have equal (with respect to \verb@equals@) primary constructor arguments. -\item[] Method \verb@hashCode: ()int@ computes a hash-code -depending on the data structure in a way which maps equal (with respect to -\verb@equals@) values to equal hash-codes. -\item[] Method \verb@toString: ()String@ returns a string representation which -contains the name of the class and its primary constructor arguments. -\end{itemize} - -\example Here is the definition of abstract syntax for lambda -calculus: - -\begin{verbatim} -class Expr; -case class - Var \=(x: String) \=extends Expr, - Apply \>(f: Expr, e: Expr) \>extends Expr, - Lambda \>(x: String, e: Expr) \>extends Expr; -\end{verbatim} -This defines a class \verb@Expr@ with case classes -\verb@Var@, \verb@Apply@ and \verb@Lambda@. A call-by-value evaluator for lambda -expressions could then be written as follows. - -\begin{verbatim} -type Env = String => Value; -case class Value(e: Expr, env: Env); - -def eval(e: Expr, env: Env): Value = e match { - case Var (x) => - env(x) - case Apply(f, g) => - val Value(Lambda (x, e1), env1) = eval(f, env); - val v = eval(g, env); - eval (e1, (y => if (y == x) v else env1(y))) - case Lambda(_, _) => - Value(e, env) -} -\end{verbatim} - -It is possible to define further case classes that extend type -\verb@Expr@ in other parts of the program, for instance -\begin{verbatim} -case class Number(x: Int) extends Expr; -\end{verbatim} - -This form of extensibility can be excluded by declaring the base class -\verb@Expr@ \verb@sealed@; in this case, the only classes permitted to -extend \verb@Expr@ are those which are nested inside \verb@Expr@, or -which appear in the same statement sequence as the definition of -\verb@Expr@. - -\section{Traits} - -\label{sec:traits} - -\syntax\begin{verbatim} - ClsDef \=::=\= trait ClassDef {`,' ClassDef} -\end{verbatim} - -A class definition which starts with the reserved word \verb@trait@ -instead of \verb@class@ defines a trait. A trait is a specific -instance of an abstract class, so the \verb@abstract@ modifier is -redundant for it. The template of a trait must satisfy the following -three restrictions. -\begin{enumerate} -\item All base classes of the trait are traits. -\item All parent class constructors of a template - must be primary constructors with empty value - parameter lists. -\item All non-empty statements in the template are either imports or pure definitions (\sref{sec:defs}). -\end{enumerate} -A {\em pure} definition can be evaluated without any side effect. -Function, type, class, or object definitions are always pure. A value -definition is pure if its right-hand side expression is pure. Pure -expressions are paths, literals, as well as typed expressions -\verb@e: T@ where \verb@e@ is pure. - -These restrictions ensure that the evaluation of the mixin constructor -of a trait has no effect. Therefore, traits may appear several times -in the base class sequence of a template, whereas other classes cannot. -%\item Packagings may add interface classes as new base classes to an -%existing class or module. - -\example\label{ex:comparable} -The following trait class defines the property of being -ordered, i.e. comparable to objects of some type. It contains an abstract method -\verb@<@ and default implementations of the other comparison operators -\verb@<=@, \verb@>@, and \verb@>=@. - -\begin{verbatim} -trait Ord[t <: Ord[t]]: t { - def < (that: t): Boolean; - def <=(that: t): Boolean = this < that || this == that; - def > (that: t): Boolean = that < this; - def >=(that: t): Boolean = that <= this; -} -\end{verbatim} - -\section{Object Definitions} -\label{sec:modules} -\label{sec:object-defs} - -\syntax\begin{verbatim} - ObjectDef \=::=\= id [`:' SimpleType] ClassTemplate -\end{verbatim} - -An object definition defines a single object of a new class. Its -most general is -\verb@object m: s extends t@. Here, -\begin{itemize} -\item[] -\verb@m@ is the name of the object to be defined. -\item[] \verb@s@ is the {\em self type} of the object. References to -\verb@m@ are assumed to have type \verb@s@. Furthermore, inside the -template \verb@t@, the type of \verb@this@ is also assumed to be \verb@s@. -The self type must conform to the self types of all classes which are -inherited by the template \verb@t@. The self type declaration -`\verb@:s@' may be omitted, in which case the self type of the class is -assumed to be equal to the anonymous class defined by \verb@t@. -\item[] -\verb@t@ is a -template (\sref{sec:templates}) of the form -\verb@sc with mc$_1$ with ... with mc$_n$ { stats }@ -which defines the base classes, behavior and initial state of \verb@m@. -The extends clause \verb@extends sc with ... with mc$_n$@ -can be omitted, in which case -\verb@extends scala.Object@ is assumed. The class body -\verb@{stats}@ may also be omitted, in which case the empty body -\verb@{}@ is assumed. -\end{itemize} -The object definition defines a single object (or: {\em module}) -conforming to the template \verb@t@. It is roughly equivalent to a class -definition and a value definition that creates an object of the class: -\begin{verbatim} -final class m$\Dollar$class: s extends t; -final val m: s = new m$\Dollar$class; -\end{verbatim} -(The \verb@final@ modifiers are omitted if the definition occurs as -part of a block. The class name \verb@m$\Dollar$class@ is not -accessible for user programs.) - -There are however two differences between an object definition and a -pair of class and value definition as the one given above. First, -object definitions may appear as top-level definitions in a -compilation unit, whereas value definitions may not. Second, the -module defined by an object definition is instantiated lazily. The -\verb@new m$\Dollar$class@ constructor is evaluated not at the point -of the object definition, but is instead evaluated the first time \verb@m@ -is dereferenced during execution of the program (which might be never -at all). An attempt to dereference \verb@m@ again in the course of -evaluation of the constructor leads to a infinite loop or run-time -error. Other threads trying to dereference \verb@m@ while the constructor -is being evaluated block until evaluation is complete. - -\example -Classes in Scala do not have static members; however, an equivalent -effect can be achieved by an accompanying object definition -E.g. -\begin{verbatim} -abstract class Point { - val x: Double; - val y: Double; - def isOrigin = (x == 0.0 && y == 0.0); -} -object Point { - val origin = new Point() with { val x = 0.0, y = 0.0 } -} -\end{verbatim} -This defines a class \verb@Point@ and an object \verb@Point@ which -contains \verb@origin@ as a member. Note that the double use of the -name \verb@Point@ is legal, since the class definition defines the name -\verb@Point@ in the type name space, whereas the object definition -defines a name in the term namespace. - -\comment{ -\example Here's an outline of a module definition for a file system. - -\begin{verbatim} -module FileSystem with { - private type FileDirectory; - private val dir: FileDirectory - - interface File with { - def read(xs: Array[Byte]) - def close: Unit - } - - private class FileHandle extends File with { ... } - - def open(name: String): File = ... -} -\end{verbatim} -} - -\chapter{Expressions} -\label{sec:exprs} - -\syntax\begin{verbatim} - Expr \=::=\= [Bindings `=>'] Expr - \> |\> if `(' Expr `)' Expr [[`;'] else Expr] - \> |\> try `{' block `}' [catch Expr] [finally Expr] - \> |\> while '(' Expr ')' Expr - \> |\> do Expr [`;'] while `(' Expr ')' - \> |\> for `(' Enumerators `)' (do | yield) Expr - \> |\> [SimpleExpr `.'] id `=' Expr - \> |\> SimpleExpr ArgumentExpr `=' Expr - \> |\> PostfixExpr [`:' Type1] - PostfixExpr \>::=\> InfixExpr [id] - InfixExpr \>::=\> PrefixExpr - \> |\> InfixExpr id InfixExpr - PrefixExpr \>::=\> [`-' | `+' | `~' | `!'] SimpleExpr - SimpleExpr \>::=\> literal - \> |\> Path - \> |\> `(' [Expr] `)' - \> |\> BlockExpr - \> |\> new Template - \> |\> SimpleExpr `.' id - \> |\> SimpleExpr TypeArgs - \> |\> SimpleExpr ArgumentExpr - ArgumentExpr \>::=\> `(' Expr ')' - \> |\> BlockExpr - BlockExpr \>::=\> `{' CaseClause {CaseClause} `}' - \> |\> `{' Block `}' - Block \>::=\> {BlockStat `;'} [Expr] - Exprs \>::= \> Expr {`,' Expr} -\end{verbatim} - -Expressions are composed of operators and operands. Expression forms are -discussed subsequently in decreasing order of precedence. - -The typing of expressions is often relative to some {\em expected -type}. When we write ``expression \verb@e@ is expected to conform to -type \verb@T@'', we mean: (1) the expected type of \verb@e@ is -\verb@T@, and (2) the type of expression \verb@e@ must conform to -\verb@T@. - -\section{Literals} - -\syntax\begin{verbatim} - SimpleExpr \=::= \= literal - literal \>::= \> intLit - \> |\> floatLit - \> |\> charLit - \> |\> stringLit - \> |\> symbolLit -\end{verbatim} - -Typing and evaluation of numeric, character, and string literals are -generally as in Java. An integer literal denotes an integer -number. Its type is normally \verb@int@. However, if the expected type -\verb@pt@ of the expression is either \verb@byte@, \verb@short@, or -\verb@char@ and the integer number fits in the numeric range defined -by the type, then the number is converted to type \verb@pt@ and the -expression's type is \verb@pt@. A floating point literal denotes a -single-precision or double precision IEEE floating point number. A -character literal denotes a Unicode character. A string literal -denotes a member of \verb@java.lang.String@. - -A symbol literal \verb@'id@ is a shorthand for the expression -\verb@scala.Symbol("id")@. If the symbol literal is followed by an -actual parameters, as in \verb@'id(args)@, then the whole expression -is taken to be a shorthand for -\verb@scala.Labelled(scala.Symbol("id"), args)@. - -\section{Boolean constants} - -\begin{verbatim} - SimpleExpr \=::= \= true | false -\end{verbatim} - -The boolean truth values are denoted by the reserved words \verb@true@ -and \verb@false@. The type of these expressions is \verb@boolean@, and -their evaluation is immediate. - -\section{The $\NULL$ Reference} - -\syntax\begin{verbatim} - SimpleExpr \=::= \= null -\end{verbatim} - -The \verb@null@ expression is of type \verb@scala.AllRef@. It -denotes a reference value which refers to a special ``null' object, -which implements methods in class \verb@scala.AnyRef@ as follows: -\begin{itemize} -\item[] -\verb@eq(x)@, \verb@==(x)@, \verb@equals(x)@ return \verb@true@ iff their -argument \verb@x@ is also the ``null'' object. -\item[] -\verb@isInstanceOf[T]@ always returns \verb@false@. -\item[] -\verb@asInstanceOf[T]@ always returns the ``null'' object itself. -\item[] -\verb@toString@ returns the string ``null''. -\end{itemize} -A reference to any other member of the ``null'' object causes a -\verb@NullPointerException@ to be thrown. - -\section{Designators} -\label{sec:designators} - -\syntax\begin{verbatim} - Designator \=::= \= Path - \> | \> SimpleExpr `.' id -\end{verbatim} - -A designator refers to a named term. It can be a {\em simple name} or -a {\em selection}. If $r$ is a stable identifier of type $T$, the -selection $r.x$ refers to the term member of $r$ that is identified in -$T$ by the name $x$. For other expressions $e$, $e.x$ is typed as if -it was $(\VAL;y=e\semi y.x)$ for some fresh name $y$. The typing rules -for blocks implies that in that case $x$'s type may not refer to any -abstract type member of \verb@e@. - -The expected type of a designator's prefix is always missing. -The -type of a designator is normally the type of the entity it refers -to. However, if the designator is a path (\sref{sec:paths}) \verb@p@, -its type is \verb@p.type@, provided the expression's expected type is -a singleton type, or \verb@p@ occurs as the prefix of a selection, -type selection, or mixin super expression. - -The selection $e.x$ is evaluated by first evaluating the qualifier -expression $e$. The selection's result is then the value to which the -selector identifier is bound in the selected object designated by $e$. - -\section{This and Super} -\label{sec:this-super} - -\syntax\begin{verbatim} - SimpleExpr \=::= \= [id `.'] this - \> | \> [id `.'] super [`[' id `]'] `.' id -\end{verbatim} - -The expression \verb@this@ can appear in the statement part of a -template or compound type. It stands for the object being defined by -the innermost template or compound type enclosing the reference. If -this is a compound type, the type of \verb@this@ is that compound type. -If it is a template of an instance creation expression, the type of -\verb@this@ is the type of that template. If it is a template of a -class or object definition with simple name \verb@C@, the type of this -is the same as the type of \verb@C.this@. - -The expression \verb@C.this@ is legal in the statement part of an -enclosing class or object definition with simple name \verb@C@. It -stands for the object being defined by the innermost such definition. -If the expression's expected type is a singleton type, or -\verb@C.this@ occurs as the prefix of a selection, its type is -\verb@C.this.type@, otherwise it is the self type of class \verb@C@. - -A reference \verb@super.m@ in a template refers to the definition of -\verb@m@ in the actual superclass (\sref{sec:base-classes}) of the -template. A reference \verb@C.super.m@ refers to the definition of -\verb@m@ in the actual superclass of the innermost enclosing class or -object definition named \verb@C@ which encloses the reference. The -definition referred to by \verb@super@ or \verb@C.super@ must be -concrete, or the template containing the reference must contain a -definition which has an \verb@override@ modifier and which overrides -\verb@m@. - -The \verb@super@ prefix may be followed by a mixin qualifier -\verb@[M]@, as in \verb@C.super[M].x@. This is called a {\em mixin -super reference}. In this case, the reference is to the member of -\verb@x@ in the (first) mixin class of \verb@C@ whose simple name -is \verb@M@. - -\example\label{ex:super} -Consider the following class definitions - -\begin{verbatim} -class Root { val x = "Root" } -class A extends Root { override val x = "A" ; val superA = super.x } -class B extends Root { override val x = "B" ; val superB = super.x } -class C extends A with B with { override val x = "C" ; val superC = super.x } -class D extends A with { val superD = super.x } -class E extends C with D with { val superE = super.x } -\end{verbatim} -Then we have: -\begin{verbatim} -new A.superA = "Root", new B.superB = "Root" -new C.superA = "Root", new C.superB = "A", new C.superC = "A" -new D.superA = "Root", new D.superD = "A" -new E.superA = "Root", new E.superB = "A", new E.superC = "A", - new E.superD = "C", new E.superE = "C" -\end{verbatim} -Note that the \verb@superB@ function returns different results -depending on whether \verb@B@ is used as defining class or as a mixin class. - -\example Consider the following class definitions: -\begin{verbatim} -class Shape { - override def equals(other: Any) = ...; - ... -} -trait Bordered extends Shape { - val thickness: int; - override def equals(other: Any) = other match { - case that: Bordered => this.thickness == that.thickness - case _ => false - } - ... -} -trait Colored extends Shape { - val color: Color; - override def equals(other: Any) = other match { - case that: Colored => this.color == that.color - case _ => false - } - ... -} -\end{verbatim} - -All three definitions of \verb@equals@ are combined in the class -below, which makes use of both plain and mixin super references. -\begin{verbatim} -trait BorderedColoredShape extends Shape with Bordered with Colored { - override def equals(other: Any) = other match { - case that: BorderedColoredShape => - super.equals(that) && - super[Bordered].equals(that) && - super[Colored].equals(that) - case _ => false - } -} -\end{verbatim} - -\section{Function Applications} -\label{sec:apply} - -\syntax\begin{verbatim} - SimpleExpr \=::= \= SimpleExpr ArgumentExpr -\end{verbatim} - -An application \verb@f(e$_1$, ..., e$_n$)@ applies the function \verb@f@ to the -argument expressions \verb@e$_1$, ..., e$_n$@. If \verb@f@ has a method type -\verb@(T$_1$, ..., T$_n$)U@, the type of each argument -expression \verb@e$_i$@ must conform to the corresponding parameter type -\verb@T$_i$@. If \verb@f@ has some value type, the application is taken to be -equivalent to \verb@f.apply(e$_1$, ..., e$_n$)@, i.e.\ the -application of an \verb@apply@ function defined by \verb@f@. - -%Class constructor functions -%(\sref{sec:classes}) can only be applied in constructor invocations -%(\sref{sec:constr-invoke}), never in expressions. - -Evaluation of \verb@f(e$_1$, ..., e$_n$)@ usually entails evaluation of -\verb@f@ and \verb@e$_1$, ..., e$_n$@ in that order. Each argument expression -is converted to the type of its corresponding formal parameter. After -that, the application is rewritten to the function's right hand side, -with actual arguments substituted for formal parameters. The result -of evaluating the rewritten right-hand side is finally converted to -the function's declared result type, if one is given. - -The case of a formal \verb@def@-parameter with a parameterless -method type \verb@[]T@ is treated specially. In this case, the -corresponding actual argument expression is not evaluated before the -application. Instead, every use of the formal parameter on the -right-hand side of the rewrite rule entails a re-evaluation of the -actual argument expression. In other words, the evaluation order for -\verb@def@-parameters is {\em call-by-name} whereas the evaluation -order for normal parameters is {\em call-by-value}. - -\section{Type Applications} -\label{sec:type-app} -\syntax\begin{verbatim} - SimpleExpr \=::= \= SimpleExpr `[' Types `]' -\end{verbatim} - -A type application \verb@e[T$_1$, ..., T$_n$]@ instantiates a -polymorphic value \verb@e@ of type -\verb@[a$_1$ >: L$_1$ <: U$_1$, ..., a$_n$ >: L$_n$ <: U$_n$]S@ with -argument types \verb@T$_1$, ..., T$_n$@. Every argument type -\verb@T$_i$@ must obey corresponding bounds \verb@L$_i$@ and -\verb@U$_i$@. That is, for each \verb@i = 1, ..., n@, we must -have \verb@L$_i \sigma$ <: T$_i$ <: U$_i \sigma$@, where $\sigma$ is the -substitution \verb@[a$_1$ := T$_1$, ..., a$_n$ := T$_n$]@. The type -of the application is \verb@S$\sigma$@. - -The function part \verb@e@ may also have some value type. In this case -the type application is taken to be equivalent to -\verb@e.apply[T$_1$, ..., T$_n$]@, i.e.\ the -application of an \verb@apply@ function defined by \verb@e@. - -Type applications can be omitted if local type inference -(\sref{sec:local-type-inf}) can infer best type parameters for a -polymorphic functions from the types of the actual function arguments -and the expected result type. - -\section{References to Overloaded Bindings} -\label{sec:overloaded-refs} - -If a name \verb@f@ referenced in an identifier or selection is -overloaded (\sref{sec:overloaded-types}), the context of the reference -has to identify a unique alternative of the overloaded binding. The -way this is done depends on whether or not \verb@f@ is used as a -function. Let $\AA$ be the set of all type alternatives of -\verb@f@. - -Assume first that \verb@f@ appears as a function in an application, as -in \verb@f(args)@. If there is precisely one alternative in -$\AA$ which is a (possibly polymorphic) method type whose arity -matches the number of arguments given, that alternative is chosen. - -Otherwise, let \verb@argtypes@ be the vector of types obtained by -typing each argument with a missing expected type. One determines -first the set of applicable alternatives. A method type alternative is -{\em applicable} if each type in \verb@argtypes@ is compatible with -the corresponding formal parameter type in the alternative, and, if -the expected type is defined, the method's result type is compatible to -it. A polymorphic method type is applicable if local type inference -can determine type arguments so that the instantiated method type is -applicable. - -Here, a type \verb@T@ is {\em compatible} to a type \verb@U@ if one of the -following three clauses applies: -\begin{enumerate} -\item -\verb@T@ conforms to \verb@U@. -\item -\verb@T@ is a parameterless method type \verb@[]T'@ and \verb@T'@ -conforms to \verb@U@. -\item -\verb@T@ is a monomorphic method type \verb@(Ts$_1$) ... (Ts$_n$)S@ which -can be converted to a function type \verb@T'@ by using the rules for -implicit conversions (\sref{sec:impl-conv}) and \verb@T'@ conforms to -\verb@U@. -\end{enumerate} - -Let $\BB$ be the set of applicable alternatives. It is an error if -$\BB$ is empty. Otherwise, one chooses the {\em most specific} -alternative among the alternatives in $\BB$, according to the -following definition of being ``more specific''. -\begin{itemize} -\item -A method type \verb@(Ts)U@ is more specific than some other -type \verb@S@ if \verb@S@ is applicable to arguments \verb@(ps)@ of -types \verb@Ts@. -\item -A polymorphic method type -\verb@[a$_1$ >: L$_1$ <: U$_1$, ..., a$_n$ >: L$_n$ <: U$_n$]T@ is -more specific than some other type \verb@S@ if \verb@T@ is more -specific than \verb@S@ under the assumption that for -\verb@i = 1, ..., n@ each \verb@a$_i$@ is an abstract type name -bounded from below by \verb@L$_i$@ and from above by \verb@U$_i$@. -\item -Any other type is always more specific than a parameterized method -type or a polymorphic type. -\end{itemize} -It is an error if there is no unique alternative in $\BB$ which is -more specific than all other alternatives in $\BB$. - -Assume next that \verb@f@ appears as a function in a type -application, as in \verb@f[targs]@. Then we choose an alternative in -$\AA$ which takes the same number of type parameters as there are -type arguments in \verb@targs@. It is an error if no such alternative -exists, or if it is not unique. - -Assume finally that \verb@f@ does not appear as a function in either -an application or a type application. If an expected type is given, -let $\BB$ be the set of those alternatives in $\AA$ which are -compatible to it. Otherwise, let $\BB$ be the same as $\AA$. -We choose in this case the most specific alternative among all -alternatives in $\BB$. It is an error if there is no unique -alternative in $\BB$ which is more specific than all other -alternatives in $\BB$. - -\example Consider the following definitions: - -\begin{verbatim} - class A extends B {} - def f(x: B, y: B) = ... - def f(x: A, y: B) = ... - val a: A, b: B -\end{verbatim} -Then the application \verb@f(b, b)@ refers to the first -definition of \verb@f@ whereas the application \verb@f(a, a)@ -refers to the second. Assume now we add a third overloaded definition -\begin{verbatim} - def f(x: B, y: A) = ... -\end{verbatim} -Then the application \verb@f(a, a)@ is rejected for being ambiguous, since -no most specific applicable signature exists. - -\section{Instance Creation Expressions} -\label{sec:inst-creation} - -\syntax\begin{verbatim} - SimpleExpr \=::= \= new Template -\end{verbatim} - -A simple instance creation expression is \verb@new c@ where \verb@c@ -is a constructor invocation (\sref{sec:constr-invoke}). Let \verb@T@ -be the type of \verb@c@. Then \verb@T@ must denote a (a type instance -of) a non-abstract subclass of \verb@scala.AnyRef@ which -conforms to its self type. The expression is evaluated by creating a -fresh object of the type \verb@T@, which is is initialized by -evaluating \verb@c@. The type of the expression is \verb@T@'s self -type (which might be less specific than \verb@T@). - -A general instance creation expression is -\verb@new sc with mc$_1$ with ... with mc$_n$ {stats}@ where -\verb@n $\geq$ 0@, \verb@sc@ as well as \verb@mc$_1$, ..., mc$_n$@ are -constructor invocations (of types \verb@S, T$_1$, ...,T$_n$@, say) and -\verb@stats@ is a statement sequence containing initializer statements -and member definitions (\sref{sec:members}). The type of such an -instance creation expression is then the compound type -\verb@S with T$_1$ with ... with T$_n$ {R}@, where \verb@{R}@ is a -refinement (\sref{sec:compound-types}) which declares exactly those -members of \verb@stats@ that override a member of \verb@S@ or -\verb@T$_1$, ..., T$_n$@. For this type to be well-formed, \verb@R@ -may not reference types defined in \verb@stats@ which do not -themselves form part of \verb@R@. - -The instance creation expression is evaluated by creating a fresh -object, which is initialized by evaluating the expression template. - -\example Consider the class -\begin{verbatim} -abstract class C { - type T; val x: T; def f(x: T): Object -} -\end{verbatim} -and the instance creation expression -\begin{verbatim} -C { type T = Int; val x: T = 1; def f(x: T): T = y; val y: T = 2 } -\end{verbatim} -Then the created object's type is: -\begin{verbatim} -C { type T = Int; val x: T; def f(x: T): T } -\end{verbatim} -The value \verb@y@ is missing from the type, since \verb@y@ does not -override a member of \verb@C@. - -\section{Blocks} -\label{sec:blocks} - -\syntax\begin{verbatim} - BlockExpr \=::= \= `{' Block `}' - Block \>::= \> [{BlockStat `;'} Expr] -\end{verbatim} - -A block expression \verb@{s$_1$; ...; s$_n$; e}@ is constructed from a -sequence of block statements \verb@s$_1$ , ..., s$_n$@ and a final -expression \verb@e@. The final expression can be omitted, in which -case the unit value \verb@()@ is assumed. - -%Whether or not the scope includes the statement itself -%depends on the kind of definition. - -The expected type of the final expression \verb@e@ is the expected -type of the block. The expected type of all preceding statements is -missing. - -The type of a block \verb@s$_1$; ...; s$_n$; e@ is usually the type of -\verb@e@. That type must be equivalent to a type which does not refer -to an entity defined locally in the block. If this condition is -violated, but a fully defined expected type is given, the type of the -block is instead assumed to be the expected type. - -Evaluation of the block entails evaluation of its statement sequence, -followed by an evaluation of the final expression \verb@e@, which -defines the result of the block. - -\example -Written in isolation, -the block \verb@{ class C extends B {...} ; new C }@ is illegal, since its type -refers to class \verb@C@, which is defined locally in the block. - -However, when used in a definition such as -\begin{verbatim} -val x: B = { class C extends B {...} ; new C } -\end{verbatim} -the block is well-formed, since the problematic type \verb@C@ can be -replaced by the expected type \verb@B@. - -\section{Prefix, Infix, and Postfix Operations} -\label{sec:infix-operations} - -\syntax\begin{verbatim} - PostfixExpr \=::=\= InfixExpr [id] - InfixExpr \>::=\> PrefixExpr - \> |\> InfixExpr id InfixExpr - PrefixExpr \>::=\> [`-' | `+' | `!' | `~'] SimpleExpr -\end{verbatim} - -Expressions can be constructed from operands and operators. A prefix -operation \verb@op e@ consists of a prefix operator \verb@op@, which -must be one of the identifiers `\verb@+@', `\verb@-@', `\verb@!@', or -`\verb@~@', and a simple expression \verb@e@. The expression is -equivalent to the postfix method application \verb@e.op@. - -Prefix operators are different from normal function applications in -that their operand expression need not be atomic. For instance, the -input sequence \verb@-sin(x)@ is read as \verb@-(sin(x))@, whereas the -function application \verb@negate sin(x)@ would be parsed as the -application of the infix operator \verb@sin@ to the operands -\verb@negate@ and \verb@(x)@. - -An infix or postfix operator can be an arbitrary identifier. Binary -operators have precedence and associativity defined as follows: - -The {\em precedence} of an operator is determined by the operator's first -character. Characters are listed below in increasing order of -precedence, with characters on the same line having the same precedence. -\begin{verbatim} - (all letters) - | - ^ - & - < > - = ! - : - + - - * / % - (all other special characters) -\end{verbatim} -That is, operators starting with a letter have lowest precedence, -followed by operators starting with `\verb@|@', etc. - -The {\em associativity} of an operator is determined by the operator's -last character. Operators ending with a colon `\verb@:@' are -right-associative. All other operators are left-associative. - -Precedence and associativity of operators determine the grouping of -parts of an expression as follows. -\begin{itemize} -\item If there are several infix operations in an -expression, then operators with higher precedence bind more closely -than operators with lower precedence. -\item If there are consecutive infix -operations \verb@e$_0$ op$_1$ e$_1$ op$_2$ ... op$_n$ e$_n$@ -with operators \verb@op$_1$, ..., op$_n$@ of the same precedence, -then all these operators must -have the same associativity. If all operators are left-associative, -the sequence is interpreted as -\verb@(...(e$_0$ op$_1$ e$_1$) op$_2$...) op$_n$ e$_n$@. -Otherwise, if all operators are right-associative, the -sequence is interpreted as -\verb@e$_0$ op$_1$ (e$_1$ op$_2$ (... op$_n$ e$_n$)...)@. -\item -Postfix operators always have lower precedence than infix -operators. E.g.\ \verb@e$_1$ op$_1$ e$_2$ op$_2$@ is always equivalent to -\verb@(e$_1$ op$_1$ e$_2$) op$_2$@. -\end{itemize} -A postfix operation \verb@e op@ is interpreted as \verb@e.op@. A -left-associative binary operation \verb@e$_1$ op e$_2$@ is interpreted as -\verb@e$_1$.op(e$_2$)@. If \verb@op@ is right-associative, the same operation is -interpreted as \verb@(val x=e$_1$; e$_2$.op(x))@, -where \verb@x@ is a fresh name. - -\section{Typed Expressions} - -\syntax\begin{verbatim} - Expr \=::= \= PostfixExpr [`:' Type1] -\end{verbatim} - -The typed expression \verb@e: T@ has type \verb@T@. The type of -expression \verb@e@ is expected to conform to \verb@T@. The result of -the expression is the value of \verb@e@ converted to type \verb@T@. - -\example Here are examples of well-typed and illegal typed expressions. - -\begin{verbatim} - 1: int \=// legal, of type int - 1: long \>// legal, of type long - // 1: string \>// illegal -\end{verbatim} - -\section{Assignments} - -\syntax\begin{verbatim} - Expr \=::= \= Designator `=' Expr - \> | \> SimpleExpr ArgumentExpr `=' Expr -\end{verbatim} - -An assignment to a simple variable \verb@x = e@ is interpreted -depending on whether \verb@x@ is defined in a block or in a -template. If \verb@x@ is a variable defined in a block, then the -assignment changes the current value of \verb@x@ to be the result of -evaluating the expression \verb@e@. The type of \verb@e@ is expected -to conform to the type of \verb@x@. If \verb@x@ is a member -of a template, the assignment \verb@x = e@ is interpreted as the -invocation \verb@x_=(e)@ of the setter function for variable \verb@x@ -(\sref{sec:vardef}). Analogously, an assignment \verb@f.x = e@ to a -field \verb@x@ is interpreted as the invocation \verb@f.x_=(e)@. - -An assignment \verb@f(args) = e@ with a function application to the -left of the ``\verb@=@' operator is interpreted as -\verb@f.update(args, e)@, i.e.\ -the invocation of an \verb@update@ function defined by \verb@f@. - -\example \label{ex:imp-mat-mul} -Here is the usual imperative code for matrix multiplication. - -\begin{verbatim} -def matmul(xss: Array[Array[double]], yss: Array[Array[double]]) = { - val zss: Array[Array[double]] = new Array(xss.length, yss.length); - var i = 0; - while (i < xss.length) { - var j = 0; - while (j < yss(0).length) { - var acc = 0.0; - var k = 0; - while (k < yss.length) { - acc = acc + xs(i)(k) * yss(k)(j); - k = k + 1 - } - zss(i)(j) = acc; - j = j + 1 - } - i = i + 1 - } - zss -} -\end{verbatim} -Desugaring the array accesses and assignments yields the following -expanded version: -\begin{verbatim} -def matmul(xss: Array[Array[double]], yss: Array[Array[double]]) = { - val zss: Array[Array[double]] = new Array(xss.length, yss.length); - var i = 0; - while (i < xss.length) { - var j = 0; - while (j < yss(0).length) { - var acc = 0.0; - var k = 0; - while (k < yss.length) { - acc = acc + xss.apply(i).apply(k) * yss.apply(k).apply(j); - k = k + 1 - } - zss.apply(i).update(j, acc); - j = j + 1 - } - i = i + 1 - } - zss -} -\end{verbatim} - -\section{Conditional Expressions} - -\syntax\begin{verbatim} - Expr \=::= \= if `(' Expr `)' Expr [[`;'] else Expr] -\end{verbatim} - -The conditional expression \verb@if (e$_1$) e$_2$ else e$_3$@ chooses -one of the values of \verb@e$_2$@ and \verb@e$_2$@, depending on the -value of \verb@e$_1$@. The condition \verb@e$_1$@ is expected to -conform to type \verb@boolean@. The then-part \verb@e$_2$@ and the -else-part \verb@e$_3$@ are both expected to conform to the expected -type of the conditional expression. The type of the conditional -expression is the least upper bound of the types of \verb@e$_1$@ and -\verb@e$_2$@. A semicolon preceding the \verb@else@ symbol of a -conditional expression is ignored. - -The conditional expression is evaluated by evaluating first -\verb@e$_1$@. If this evaluates to \verb@true@, the result of -evaluating \verb@e$_2$@ is returned, otherwise the result of -evaluating \verb@e$_3$@ is returned. - -A short form of the conditional expression eliminates the -else-part. The conditional expression \verb@if (e$_1$) e$_2$@ is -evaluated as if it was \verb@if (e$_1$) e$_2$ else ()@. The type of -this expression is \verb@unit@ and the then-part -\verb@e$_2$@ is also expected to conform to type \verb@unit@. - -\section{While Loop Expressions} - -\syntax\begin{verbatim} - Expr \=::= \= while `(' Expr ')' Expr -\end{verbatim} - -The while loop expression \verb@while (e$_1$) e$_2$@ is typed and -evaluated as if it was an application of \verb@whileLoop (e$_1$) (e$_2$)@ where -the hypothetical function \verb@whileLoop@ is defined as follows. - -\begin{verbatim} - def whileLoop(def c: boolean)(def s: unit): unit = - if (c) { s ; while(c)(s) } else {} -\end{verbatim} - -\example The loop -\begin{verbatim} - while (x != 0) { y = y + 1/x ; x = x - 1 } -\end{verbatim} -Is equivalent to the application -\begin{verbatim} - whileLoop (x != 0) { y = y + 1/x ; x = x - 1 } -\end{verbatim} -Note that this application will never produce a division-by-zero -error at run-time, since the -expression \verb@(y = 1/x)@ will be evaluated in the body of -\verb@while@ only if the condition parameter is false. - -\section{Do Loop Expressions} - -\syntax\begin{verbatim} - Expr \=::= \= do Expr [`;'] while `(' Expr ')' -\end{verbatim} - -The do loop expression \verb@do e$_1$ while (e$_2$)@ is typed and -evaluated as if it was the expression \verb@(e$_1$ ; while (e$_2$) e$_1$)@. -A semicolon preceding the \verb@while@ symbol of a do loop expression is ignored. - -\section{Comprehensions} - -\syntax\begin{verbatim} - Expr \=::= \= for `(' Enumerators `)' (do | yield) Expr - Enumerator \>::=\> Generator {`;' Enumerator} - Enumerator \>::=\> Generator - \> |\> Expr - Generator \>::=\> val Pattern `<-' Expr -\end{verbatim} - -A comprehension \verb@for (ens) yield e@ evaluates expression \verb@e@ for each -binding generated by the enumerators \verb@ens@. An enumerator is a generator, -possibly followed by further generators or filters. A generator -\verb@val p <- e@ produces bindings from an expression \verb@e@ which is -matched in some way against pattern \verb@p@. Filters are expressions which -restrict enumerated bindings. The precise meaning of generators and -filters is defined by translation to invocations of four methods: -\verb@map@, \verb@filter@, \verb@flatMap@, and \verb@foreach@. These -methods can be implemented in different ways for different carrier -types. As an example, an implementation of these methods for lists is -given in \sref{cls-list}. - -The translation scheme is as follows. -In a first step, every generator \verb@val p <- e@, where \verb@p@ is not -a pattern variable, is replaced by -\begin{verbatim} -val p <- e.filter { case p => true; case _ => false } -\end{verbatim} -Then, the following -rules are applied repeatedly until all comprehensions have been eliminated. -\begin{itemize} -\item -A generator \verb@q <- e@ followed by a filter \verb@f@ is translated to -a single generator \verb@q <- e.filter(x$_1$, ..., x$_n$ => f)@ where -\verb@x$_1$, ..., x$_n$@ are the free variables of \verb@q@. - -\item -A for-comprehension -\verb@for (val p <- e) yield e'@ -is translated to -\verb@e.map { case p => e' }@. - -\item -A for-comprehension -\verb@for (val p <- e) do e'@ -is translated to -\verb@e.foreach { case p => e' }@. - -\item -A for-comprehension -\begin{verbatim} -for (val p <- e; val p' <- e' ...) yield e'' , -\end{verbatim} -where \verb@...@ is a (possibly empty) -sequence of generators or filters, -is translated to -\begin{verbatim} -e.flatmap { case p => for (val p' <- e' ...) yield e'' } . -\end{verbatim} -\item -A for-comprehension -\begin{verbatim} -for (val p <- e; val p' <- e' ...) do e'' . -\end{verbatim} -where \verb@...@ is a (possibly empty) -sequence of generators or filters, -is translated to -\begin{verbatim} -e.foreach { case p => for (val p' <- e'...) do e'' } . -\end{verbatim} -\end{itemize} - -\example -the following code produces all pairs of numbers -between \verb@1@ and \verb@n-1@ whose sums are prime. -\begin{verbatim} -for \= { \= val i <- range(1, n); - \> \> val j <- range(1, i); - \> \> isPrime(i+j) -} yield Pair (i, j) -\end{verbatim} -The for-comprehension is translated to: -\begin{verbatim} -range(1, n) - .flatMap { - case i => range(1, i) - .filter { j => isPrime(i+j) } - .map { case j => Pair(i, j) } } -\end{verbatim} - -\comment{ -\example -\begin{verbatim} -package class List[a] with { - def map[b](f: (a)b): List[b] = match { - case <> => <> - case x :: xs => f(x) :: xs.map(f) - } - def filter(p: (a)Boolean) = match { - case <> => <> - case x :: xs => if p(x) then x :: xs.filter(p) else xs.filter(p) - } - def flatMap[b](f: (a)List[b]): List[b] = - if (isEmpty) Nil - else f(head) ::: tail.flatMap(f); - } - def foreach(f: (a)Unit): Unit = - if (isEmpty) () - else (f(head); tail.foreach(f)); -} -\end{verbatim} - -\example -\begin{verbatim} -abstract class Graph[Node] { - type Edge = (Node, Node) - val nodes: List[Node] - val edges: List[Edge] - def succs(n: Node) = for ((p, s) <- g.edges, p == n) s - def preds(n: Node) = for ((p, s) <- g.edges, s == n) p -} -def topsort[Node](g: Graph[Node]): List[Node] = { - val sources = for (n <- g.nodes, g.preds(n) == <>) n - if (g.nodes.isEmpty) <> - else if (sources.isEmpty) new Error(``topsort of cyclic graph'') throw - else sources :+: topsort(new Graph[Node] with { - val nodes = g.nodes diff sources - val edges = for ((p, s) <- g.edges, !(sources contains p)) (p, s) - }) -} -\end{verbatim} -} - -\example For comprehensions can be used to express vector -and matrix algorithms concisely. -For instance, here is a function to compute the transpose of a given matrix: - -\begin{verbatim} -def transpose[a](xss: Array[Array[a]]) { - for (val i <- Array.range(0, xss(0).length)) yield - Array(for (val xs <- xss) yield xs(i)) -\end{verbatim} - -Here is a function to compute the scalar product of two vectors: -\begin{verbatim} -def scalprod(xs: Array[double], ys: Array[double]) { - var acc = 0.0; - for (val Pair(x, y) <- xs zip ys) do acc = acc + x * y; - acc -} -\end{verbatim} - -Finally, here is a function to compute the product of two matrices. Compare with the imperative version of \ref{ex:imp-mat-mul}. -\begin{verbatim} -def matmul(xss: Array[Array[double]], yss: Array[Array[double]]) = { - val ysst = transpose(yss); - for (val xs <- xs) yield - for (val yst <- ysst) yield - scalprod(xs, yst) -} -\end{verbatim} -The code above makes use of the fact that \verb@map@, \verb@flatmap@, -\verb@filter@, and \verb@foreach@ are defined for members of class -\verb@scala.Array@. - -\section{Try Expressions} - -\syntax\begin{verbatim} - Expr \=::= \= try `{' block `}' [catch Expr] [finally Expr] -\end{verbatim} - -A try expression \verb@try { b } catch e@ evaluates the block -\verb@b@. If evaluation of \verb@b@ does not cause an exception to be -thrown, the result of \verb@b@ is returned. Otherwise the {\em -handler} \verb@e@ is applied to the thrown exception. Let \verb@pt@ -be the expected type of the try expression. The block \verb@b@ is -expected to conform to \verb@pt@. The handler \verb@e@ is expected -conform to type \verb@scala.PartialFunction[scala.Throwable, pt]@. -The type of the try expression is the least upper bound of the type of -\verb@b@ and the result type of \verb@e@. - -A try expression \verb@try { b } finally e@ evaluates the block -\verb@b@. If evaluation of \verb@b@ does not cause an exception to be -thrown, expression \verb@e@ is evaluated. If an exception is thrown -during evaluation of \verb@e@, the evaluation of the try expression is -aborted with the thrown exception. If no exception is thrown during -evaluation of \verb@e@, the result of \verb@b@ is returned as the -result of the try expression. If an exception is thrown during -evaluation of \verb@b@, the finally block -\verb@e@ is also evaluated. If another exception \verb@e@ is thrown -during evaluation of \verb@e@, evaluation of the try expression is -aborted with the thrown exception. If no exception is thrown during -evaluation of \verb@e@, the original exception thrown in \verb@b@ is -re-thrown once evaluation of \verb@e@ has completed. The block -\verb@b@ is expected to conform to the expected type of the try -expression. The finally expression \verb@e@ is expected to conform to -type \verb@unit@. - -A try expression \verb@try { b } catch e$_1$ finally e$_2$@ is a shorthand -for \verb@try { try { b } catch e$_1$ } finally e$_2$@. - -\section{Anonymous Functions} -\label{sec:closures} - -\syntax\begin{verbatim} - Expr \=::= \= [Bindings `=>'] Expr - Bindings \>::=\> `(' Binding {`,' Binding `)' - \> |\> id [`:' Type1] - Binding \>::= \> id [`:' Type] -\end{verbatim} - -The anonymous function \verb@(x$_1$: T$_1$, ..., x$_n$: T$_n$) => e@ -maps parameters \verb@x$_i$@ of types \verb@T$_i$@ to a result given -by expression \verb@e@. The scope of each formal parameter -\verb@x$_i$@ is \verb@e@. - -If the expected type of the anonymous function is of the form -\verb@scala.Function$\,n$[S$_1$, ..., S$_n$, R]@, the expected types -of \verb@e@ is \verb@R@ and the type \verb@T$_i$@ of any of the -parameters \verb@x$_i$@ can be omitted, in which case -\verb@T$_i$ = S$_i$@ is assumed. If the expected type of the anonymous -function is some other type, all formal parameter types must be -explicitly given, and the expected type of \verb@e@ is missing. The -type of the anonymous function is -\verb@scala.Function$\,n$[S$_1$, ..., S$_n$, T]@, where \verb@T@ is -the type of \verb@e@. \verb@T@ must be equivalent to a type which does -not refer to any of the formal parameters \verb@x$_i$@. - -The anonymous function is evaluated as the instance creation expression -\begin{verbatim} -scala.Function$\,n$[T$_1$, ..., T$_n$, T] { - def apply(x$_1$: T$_1$, ..., x$_n$: T$_n$): T = e -} -\end{verbatim} -In the case of a single formal parameter, \verb@(x: T) => e@ and \verb@(x) => e@ -can be abbreviated to \verb@x: T => e@, and \verb@x => e@, respectively. - -\example Examples of anonymous functions: - -\begin{verbatim} - x => x \=// The identity function - - f => g => x => f(g(x)) \>// Curried function composition - - (x: Int,y: Int) => x + y \>// A summation function - - () => { count = count + 1; count } \>// The function which takes an empty - \>// parameter list $()$, increments a non-local - \>// variable count and returns the new value. -\end{verbatim} - -\section{Statements} -\label{sec:statements} - -\syntax\begin{verbatim} - BlockStat \=::= \= Import - \> | \> Def - \> | \> {LocalModifier} ClsDef - \> | \> Expr - \> | \> - TemplateStat \>::= \> Import - \> | \> {Modifier} Def - \> | \> {Modifier} Dcl - \> | \> Expr - \> | \> -\end{verbatim} - -Statements occur as parts of blocks and templates. A statement can be -an import, a definition or an expression, or it can be empty. -Statements used in the template of a class definition can also be -declarations. An expression that is used as a statement can have an -arbitrary value type. An expression statement $e$ is evaluated by -evaluating $e$ and discarding the result of the evaluation. - -Block statements may be definitions which bind local names in the -block. The only modifiers allowed in block-local definitions are modifiers -\verb@abstract@, \verb@final@, or \verb@sealed@ preceding a class or -object definition. - -With the exception of overloaded definitions -(\sref{sec:overloaded-defs}), a statement sequence making up a block -or template may not contain two definitions or declarations that bind -the same name in the same namespace. Evaluation of a statement -sequence entails evaluation of the statements in the order they are -written. - -\chapter{Pattern Matching} - -\section{Patterns} - -% 2003 July - changed to new pattern syntax + semantic Burak - -\label{sec:patterns} - -\syntax\begin{verbatim} -Pattern \=::= \= TreePattern { `|' TreePattern } - -TreePattern \>::= \> varid `:' Type - \> | \> `_' `:' Type - \> | \> SimplePattern [ '*' | '?' | '+' ] - \> | \> SimplePattern { id SimplePattern } - -SimplePattern \=::= \> varid [ '@' SimplePattern ] - \> | \> `_' - \> | \> literal - \> | \> StableId [ `(' [Patterns] `)' ] - \> | \> `(' Patterns `)' - \> | \> - - Patterns \>::= \> Pattern {`,' Pattern} -\end{verbatim} - -A pattern is built from constants, constructors, variables and regular -operators. Pattern matching tests whether a given value (or sequence -of values) has the shape defined by a pattern, and, if it does, binds -the variables in the pattern to the corresponding components of the -value (or sequence of values). The same variable name may not be -bound more than once in a pattern. - -The type of a pattern and the expected types of variables within the -pattern are determined by the context, except for patterns -that employ regular operators. In the latter case the missing -information is provided by the structure of the pattern. -We distinguish the following kinds of patterns. - -A {\em wild-card pattern} \_ matches any value. - -A {\em variable-binding pattern} $x @ p$ is a simple identifier $x$ -which starts with a lower case letter, together with a pattern $p$. It -matches a value or a sequence of values whenever $p$ does, and in -addition binds the variable name to that value or to that sequence of -values. The type of $x$ is either $T$ as determined from the context, or -\verb@List[T]@ \todo{really?}, if $p$ matches sequences of values. A -special case is a {\em variable pattern} $x$ which is treated as $x @ \_$. - -A {\em typed pattern} $x: T$ consists of a pattern variable $x$ and a -simple type $T$. The type $T$ may be a class type or a compound type; -it may not contain a refinement (\sref{sec:refinements}). This -pattern matches any non-null value of type $T$ and binds the variable -name to that value. $T$ must conform to the pattern's expected -type. The type of $x$ is $T$. - -A {\em pattern literal} $l$ matches any value that is equal (in terms -of $==$) to it. It's type must conform to the expected type of the -pattern. - -A {\em named pattern constant} $p$ is a stable identifier -(\sref{sec:stableids}). To resolve the syntactic overlap with a -variable pattern, a named pattern constant may not be a simple name -starting with a lower-case letter. The stable identifier $p$ is -expected to conform to the expected type of the pattern. The pattern -matches any value $v$ such that \verb@$r$ == $v$@ -(\sref{sec:cls-object}). - -A {\em sequence pattern} $p_1 \commadots p_n$ where $n \geq 0$ is a -sequence of patterns separated by commas and matching the sequence of -values that are matched by the components. Sequence pattern may only -appear under constructor applications. Note that empty sequence -patterns are allowed. The type of the value patterns \todo{where defined?} -that appear in -the pattern is the expected type as determined from the context. - -A {\em choice pattern} $p_1 | \ldots | p_n$ is a choice among several -alternatives, which may not contain variable-binding patterns. It -matches every value matched by at least one of its alternatives. Note -that the empty sequence may appear as an alternative. An {\em option -pattern} $p?$ is an abbreviation for $(p| )$. If the alternatives -are value patterns, then the whole choice pattern is a value pattern, -whose type is the least upper bound of the types of the alternatives. - -An {\em iterated pattern} $p*$ matches the sequence of values -consisting of zero, one or more occurrences of values matched by $p$, -where $p$ may not contain a variable-binding pattern. A {\em non-empty -iterated pattern} $p+$ is an abbreviation for $(p,p*)$. - -A non-regular sequence \todo{find other term?} -pattern is a sequence pattern $p_1 \commadots p_n$ -where $n \geq 1$ with no component pattern containing iterated or nested -sequence patterns. - -A {\em constructor pattern} $c ( p )$ consists of a simple type $c$ -followed by a pattern $p$. If $c$ designates a monomorphic case -class, then it must conform to the expected type of the pattern, the -pattern must be a non-regular sequence pattern $p_1 \commadots p_n$ -whose length corresponds to the number of arguments of $c$'s primary -constructor. The expected types of the component patterns are then -taken from the formal parameter types of (said) constructor. If $c$ -designates a polymorphic case class, then there must be a unique type -application instance of it such that the instantiation of $c$ conforms -to the expected type of the pattern. The instantiated formal parameter -types of $c$'s primary constructor are then taken as the expected -types of the component patterns $p_1\commadots p_n$. In both cases, -the pattern matches all objects created from constructor invocations -$c(v_1 \commadots v_n)$ where each component pattern $p_i$ matches the -corresponding value $v_i$. If $c$ does not designate a case class, it -must be a subclass of \verb@Seq[ T ]@. In that case $p$ may be an -arbitrary pattern. Value patterns in $p$ are expected to conform to -type $T$, and the pattern matches all objects whose \verb@elements()@ -method returns a sequence that matches $p$. - -The pattern $(p)$ is regarded as equivalent to the pattern $p$, if $p$ -is a nonempty sequence pattern. The empty tuple $()$ is a shorthand -for the constructor pattern \verb@Unit@. - -An {\em infix operation pattern} \verb@p id p'@ is a shorthand for the -constructor pattern \verb@id(p, p')@. The precedence and -associativity of operators in patterns is the same as in expressions -(\sref{sec:infix-operations}). The operands may not be empty sequence -patterns. - -Regular expressions that contain variable bindings may be ambiguous, -i.e. there might be several ways to match a sequence against the -pattern. In these cases, the \emph{shortest-match policy} applies: -patterns that appear before other, overlapping patterns match -as little as possible. - -\example Some examples of patterns are: -\begin{enumerate} -\item -The pattern \verb@ex: IOException@ matches all instances of class -\verb@IOException@, binding variable \verb@ex@ to the instance. -\item -The pattern \verb@Pair(x, _)@ matches pairs of values, binding \verb@x@ to -the first component of the pair. The second component is matched -with a wildcard pattern. -\item -The pattern \verb+List( x, y, xs @ _ * )+ matches lists of length $\geq 2$, -binding \verb@x@ to the list's first element, \verb@y@ to the list's -second element, and \verb@xs@ to the remainder, which may be empty. -\item -The pattern \verb=List( 1, x@(( 'a' | 'b' )+),y,_ )= matches a list that -contains 1 as its first element, continues with a non-empty sequence of -\verb@'a'@s and \verb@'b'@s, followed by two more elements. The sequence 'a's and 'b's -is bound to \verb@x@, and the next to last element is bound to \verb@y@. -\item -The pattern \verb=List( x@( 'a'* ), 'a'+ )= matches a non-empty list of -\verb@'a'@s. Because of the shortest match policy, \verb@x@ will always be bound to -the empty sequence. -\item -The pattern \verb=List( x@( 'a'+ ), 'a'* )= also matches a non-empty list of -\verb@'a'@s. Here, \verb@x@ will always be bound to -the sequence containing one \verb@'a'@ -\end{enumerate} - -\subsection{Pattern Matching Expressions} -\label{sec:pattern-match} - -\syntax\begin{verbatim} - BlockExpr \=::=\= `{' CaseClause {CaseClause} `}' - CaseClause \>::=\> case Pattern [`if' PostfixExpr] `=>' Block -\end{verbatim} - -A pattern matching expression -\verb@case p$_1$ => b$_1$ ... case p$_n$ => b$_n$@ consists of a number -$n \geq 1$ of cases. Each case consists of a (possibly guarded) pattern -$p_i$ and a block $b_i$. The scope of the pattern variables in $p_i$ is -the corresponding block $b_i$. - -The expected type of a pattern matching expression must in part be -defined. It must be either \verb@scala.Function1[T$_p$, T$_r$]@ or -\verb@scala.PartialFunction[T$_p$, T$_r$]@, where the argument type -\verb@T$_p$@ must be fully determined, but the result type -\verb@T$_r$@ may be undetermined. All patterns are typed -relative to the expected type $T_p$ (\sref{sec:patterns}). The expected type of -every block \verb@b$_i$@ is \verb@T$_r$@. -Let \verb@T$_b$@ be the least upper bound of the types of all blocks -\verb@b$_i$@. The type of the pattern matching expression is -then the required type with \verb@T$_r$@ replaced by \verb@T$_b$@ -(i.e. the type is either \verb@scala.Function[T$_p$, T$_b$]@ or -\verb@scala.PartialFunction[T$_p$, T$_b$]@. - -When applying a pattern matching expression to a selector value, -patterns are tried in sequence until one is found which matches the -selector value (\sref{sec:patterns}). Say this case is $\CASE;p_i -\Arrow b_i$. The result of the whole expression is then the result of -evaluating $b_i$, where all pattern variables of $p_i$ are bound to -the corresponding parts of the selector value. If no matching pattern -is found, a \verb@scala.MatchError@ exception is thrown. - -The pattern in a case may also be followed by a guard suffix \verb@if e@ -with a boolean expression $e$. The guard expression is evaluated if -the preceding pattern in the case matches. If the guard expression -evaluates to \verb@true@, the pattern match succeeds as normal. If the -guard expression evaluates to \verb@false@, the pattern in the case -is considered not to match and the search for a matching pattern -continues. - -\comment{ -A case with several patterns $\CASE;p_1 \commadots p_n ;\IF; e \Arrow b$ is a -shorthand for a sequence of single-pattern cases $\CASE;p_1;\IF;e \Arrow b -;\ldots; \CASE;p_n ;\IF;e\Arrow b$. In this case none of the patterns -$p_i$ may contain a named pattern variable (but the patterns may contain -wild-cards). -} - -In the interest of efficiency the evaluation of a pattern matching -expression may try patterns in some other order than textual -sequence. This might affect evaluation through -side effects in guards. However, it is guaranteed that a guard -expression is evaluated only if the pattern it guards matches. - -\example -Often, pattern matching expressions are used as arguments -of the \verb@match@ method, which is predefined in class \verb@Any@ -(\sref{sec:cls-object}) and is implemented there by postfix function -application. Here is an example: -\begin{verbatim} -def length [a] (xs: List[a]) = xs match { - case Nil => 0 - case x :: xs1 => 1 + length (xs1) -} -\end{verbatim} - -\chapter{Top-Level Definitions} -\label{sec:topdefs} - -\syntax\begin{verbatim} - CompilationUnit \=::=\= [package QualId `;'] {TopStat `;'} TopStat - TopStat \>::=\> {Modifier} ClsDef - \> |\> Import - \> |\> Packaging - \> |\> - QualId \>::=\> id {`.' id} -\end{verbatim} - -A compilation unit consists of a sequence of packagings, import -clauses, and class and object definitions, which may be preceded by a -package clause. - -A compilation unit \verb@package p; stats@ starting with a package -clause is equivalent to a compilation unit consisting of a single -packaging \verb@package p { stats }@. - -Implicitly imported into every compilation unit are, in that order: -the package \verb@java.lang@, the package \verb@scala@, and the object -\verb@scala.Predef@ (\sref{cls-predef}). Members of a later import in -that order hide members of an earlier import. - -\section{Packagings} - -\syntax\begin{verbatim} - Packaging \=::= \= package QualId `{' {TopStat `;'} TopStat `}' -\end{verbatim} - -A package is a special object which defines a set of member classes, -objects and packages. Unlike other objects, packages are not introduced -by a definition. Instead, the set of members of a package is determined by -packagings. - -A packaging \verb@package p { ds }@ injects all definitions in -\verb@ds@ as members into the package whose qualified name is -\verb@p@. If a definition in \verb@ds@ is labeled \verb@private@, it -is visible only for other members in the package. - -Selections \verb@p.m@ from \verb@p@ as well as imports from \verb@p@ -work as for objects. However, unlike other objects, packages may not -be used as values. It is illegal to have a package with the same fully -qualified name as a module or a class. - -Top-level definitions outside a packaging are assumed to be injected -into a special empty package. That package cannot be named and -therefore cannot be imported. However, members of the empty package -are visible to each other without qualification. - -\example The following example will create a hello world program as -function \verb@main@ of module \verb@test.HelloWorld@. -\begin{verbatim} -package test; - -object HelloWord { - def main(args: Array[String]) = System.out.println("hello world") -} -\end{verbatim} - -\end{document} - -\chapter{Local Type Inference} -\label{sec:local-type-inf} - -This needs to be specified in detail. -Essentially, similar to what is done for GJ. - -\comment{ -\section{Definitions} - -For a possibly recursive definition such as $\LET;x_1 = e_1 -;\ldots; \LET x_n = e_n$, local type inference proceeds as -follows. -A first phase assigns {\em a-priori types} to the $x_i$. The a-priori -type of $x$ is the declared type of $x$ if a declared type is -given. Otherwise, it is the inherited type, if one is -given. Otherwise, it is undefined. - -A second phase assigns completely defined types to the $x_i$, in some -order. The type of $x$ is the a-priori type, if it is completely -defined. Otherwise, it is the a-priori type of $x$'s right hand side. -The a-priori type of an expression $e$ depends on the form of $e$. -\begin{enumerate} -\item -The a-priori type of a -typed expression $e:T$ is $T$. -\item -The a-priori type of a class instance -creation expression $c;\WITH;(b)$ is $C;\WITH;R$ where $C$ is the -type of the class given in $c$ and $R$ is the a-priori type of block -$b$. -\item -The a-priori type of a block is a record consisting the a-priori -types of each non-private identifier which is declared in the block -and which is visible at in last statement of the block. Here, it is -required that every import clause $\IMPORT;e_1 \commadots e_n$ refers -to expressions whose type can be computed with the type information -determined so far. Otherwise, a compile time error results. -\item -The a-priori type of any other expression is the expression's type, if -that type can be computed with the type information determined so far. -Otherwise, a compile time error results. -\end{enumerate} -The compiler will find an ordering in which types are assigned without -compiler errors to all variables $x_1 \commadots x_n$, if such an -ordering exists. This can be achieved by lazy evaluation. -} - -\chapter{The Scala Standard Library} - -The Scala standard library consists of the package \verb@scala@ with a -number of classes and modules. - -\section{Root Classes} -\label{sec:cls-root} -\label{sec:cls-any} -\label{sec:cls-object} - -The root of the Scala class hierarchy is formed by class \verb@Any@. -Every class in a Scala execution environment inherits directly or -indirectly from this class. Class \verb@Any@ has exactly two direct -subclasses: \verb@AnyRef@ and\verb@AnyVal@. - -The subclass \verb@AnyRef@ represents all values which are represented -as objects in the underlying host system. The type of the \verb@null@ -value copnforms to every subclass of \verb@AnyRef@. A direct subclass -of -\verb@AnyRef@ is class \verb@Object@. Every user-defined Scala -class inherits directly or indirectly from this class. Classes written -in other languages still inherit from \verb@scala.AnyRef@, but not -necessarily from \verb@scala.Object@. - -The class \verb@AnyVal@ has a fixed number subclasses, which describe -values which are not implemented as objects in the underlying host -system. - -Classes \verb@AnyRef@ and \verb@AnyVal@ are required to provide only -the members declared in class \verb@Any@, but implementations may add -host-specific methods to these classes (for instance, an -implementation may identify class \verb@AnyRef@ with its own root -class for objects). - -The standard interfaces of these root classes is described by the -following definitions. - -\begin{verbatim} -abstract class Any with { - /** Get runtime type descriptor */ - def getType: Type = ... - - /** Reference equality */ - def eq (that: Any): Boolean = ... - - /** Hash code */ - def def hashCode: Int = ... -\end{verbatim} -\begin{verbatim} - /** Type test */ - def is [a]: Boolean = ... - - /** Type cast */ - def as[a]: a = if (is[a]) ... else new CastException() throw - - /** Semantic equality between values of same type */ - def == (that: Any): Boolean = this equals that - - /** Semantic inequality between values of same type */ - def != (that: Any): Boolean = !(this == that) - - /** Semantic equality between arbitrary values */ - def equals (that: Any): Boolean = ... - - /** Representation as string */ - def toString: String = getType.toString ++ "@" ++ hashCode - - /** Concatenation of string representations */ - final def + (that: Any) = toString.concat(that) - - /** Pattern matching application */ - final def match [a] (f: (Any)a): a = f(this) -} -final class AnyVal extends Any -class AnyRef extends Any -class Object extends AnyRef -\end{verbatim} - - -\section{Value Classes} -\label{sec:cls-value} - -Value classes are classes whose instances are not represented as -objects by the underlying host system. All value classes inherit from -class \verb@AnyVal@. Scala implementations need to provide the -following value classes (but are free to provide others as well). - -\begin{verbatim} -final class Unit extends AnyVal with { ... } -final class Boolean extends AnyVal with { ... } -final class Double extends AnyVal with { ... } -final class Float extends Double with { ... } -final class Long extends Float with { ... } -final class Int extends Long with { ... } -final class Char extends Int with { ... } -final class Short extends Int with { ... } -final class Byte extends Short with { ... } -\end{verbatim} - -These classes are defined in the following. - -\subsection{Class \prog{Double}} - -\begin{verbatim} -final class Double extends AnyVal with Ord with { - def asDouble: Double \=// convert to Double - def asFloat: Float \>// convert to Float - def asLong: Long \>// convert to Long - def asInt: Int \>// convert to Int - def asChar: Char \>// convert to Char - def asShort: Short \>// convert to Short - def asByte: Byte \>// convert to Byte - - def + (that: Double): Double \>// double addition - def - (that: Double): Double \>// double subtraction - def * (that: Double): Double \>// double multiplication - def / (that: Double): Double \>// double division - def % (that: Double): Double \>// double remainder - - def == (that: Double): Boolean \>// double equality - def != (that: Double): Boolean \>// double inequality - def < (that: Double): Boolean \>// double less - def > (that: Double): Boolean \>// double greater - def <= (that: Double): Boolean \>// double less or equals - def >= (that: Double): Boolean \>// double greater or equals - - def - : Double = 0.0 - this \>// double negation - def + : Double = this -} -\end{verbatim} - -\subsection{Class \prog{Float}} - -\begin{verbatim} -final class Float extends Double with { - def asDouble: Double \=// convert to Double - def asFloat: Float \>// convert to Float - def asLong: Long \>// convert to Long - def asInt: Int \>// convert to Int - def asChar: Char \>// convert to Char - def asShort: Short \>// convert to Short - def asByte: Byte \>// convert to Byte - - def + (that: Double): Double = asDouble + that - def + (that: Float): Double \>// float addition - /* analogous for -, *, /, % */ - - def == (that: Double): Boolean = asDouble == that - def == (that: Float): Boolean \>// float equality - /* analogous for !=, <, >, <=, >= */ - - def - : Float = 0.0f - this \>// float negation - def + : Float = this -} -\end{verbatim} - -\subsection{Class \prog{Long}} - -\begin{verbatim} -final class Long extends Float with { - def asDouble: Double \=// convert to Double - def asFloat: Float \>// convert to Float - def asLong: Long \>// convert to Long - def asInt: Int \>// convert to Int - def asChar: Char \>// convert to Char - def asShort: Short \>// convert to Short - def asByte: Byte \>// convert to Byte - - def + (that: Double): Double = asDouble + that - def + (that: Float): Double = asFloat + that - def + (that: Long): Long = \>// long addition - /* analogous for -, *, /, % */ - - def << (cnt: Int): Long \>// long left shift - def >> (cnt: Int): Long \>// long signed right shift - def >>> (cnt: Int): Long \>// long unsigned right shift - def & (that: Long): Long \>// long bitwise and - def | (that: Long): Long \>// long bitwise or - def ^ (that: Long): Long \>// long bitwise exclusive or - - def == (that: Double): Boolean = asDouble == that - def == (that: Float): Boolean = asFloat == that - def == (that: Long): Boolean \>// long equality - /* analogous for !=, <, >, <=, >= */ - - def - : Long = 0l - this \>// long negation - def + : Long = this -} -\end{verbatim} - - -\subsection{Class \prog{Int}} - -\begin{verbatim} -class Int extends Long with { - def asDouble: Double \=// convert to Double - def asFloat: Float \>// convert to Float - def asLong: Long \>// convert to Long - def asInt: Int \>// convert to Int - def asChar: Char \>// convert to Char - def asShort: Short \>// convert to Short - def asByte: Byte \>// convert to Byte - - def + (that: Double): Double = asDouble + that - def + (that: Float): Double = asFloat + that - def + (that: Long): Long = \>// long addition - def + (that: Int): Int = \>// long addition - /* analogous for -, *, /, % */ - - def << (cnt: Int): Int \>// long left shift - /* analogous for >>, >>> */ - - def & (that: Long): Long = asLong & that - def & (that: Int): Int \>// bitwise and - /* analogous for |, ^ */ - - def == (that: Double): Boolean = asDouble == that - def == (that: Float): Boolean = asFloat == that - def == (that: Long): Boolean \>// long equality - /* analogous for !=, <, >, <=, >= */ - - def - : Long = 0l - this \>// long negation - def + : Long = this -} -\end{verbatim} - -\subsection{Class \prog{Boolean}} -\label{sec:cls-boolean} - -\begin{verbatim} -abstract final class Boolean extends AnyVal with Ord with { - def ifThenElse[a](def t: a)(def e: a): a - - def ifThen(def t: Unit): Unit = ifThenElse(t)() - - def && (def x: Boolean): Boolean = ifThenElse(x)(False) - def || (def x: Boolean): Boolean = ifThenElse(True)(x) - def ! (def x: Boolean): Boolean = ifThenElse(False)(True) - - def == (x: Boolean): Boolean = ifThenElse(x)(x.!) - def != (x: Boolean): Boolean = ifThenElse(x.!)(x) - def < (x: Boolean): Boolean = ifThenElse(False)(x) - def > (x: Boolean): Boolean = ifThenElse(x.!)(False) - def <= (x: Boolean): Boolean = ifThenElse(x)(True) - def >= (x: Boolean): Boolean = ifThenElse(True)(x.!) -} -case class True extends Boolean with { def ifThenElse(t)(e) = t } -case class False extends Boolean with { def ifThenElse(t)(e) = e } -\end{verbatim} - - -\comment{ -\section{Reflection} - -\subsection{Classes \prog{Type}, \prog{Class}, \prog{CompoundType}} - -\begin{verbatim} -class Type[A] with { - def isSubType [B] (that: Type[B]): Boolean = ... -} -\end{verbatim} - -\begin{verbatim} -class Class[A] extends Type[A] with { - ... -} -\end{verbatim} - -\begin{verbatim} -abstract class CompoundType[A] extends Type[A] with { - def components: List[Class[A]] - ... -} -\end{verbatim} -} -\section{Other Standard Classes} - -\subsection{Class \prog{Unit} and the \prog{Tuple} Classes} -\label{sec:cls-tuple} - -\begin{verbatim} -case class Unit with { - def toString = "()" -} -case class Tuple$\,n$[a$_1$, ..., a$_n$](x$_1$: a$_1$, ..., x$_n$: a$_n$) with { - def $\_1$: a$_1$ = x$_1$ - ... - def $\_n$: a$_n$ = x$_n$ - def toString = "(" ++ x$_1$ ++ "," ++ ... ++ x$_n$ ++ ")" -} -\end{verbatim} - -\subsection{The \prog{Function} Classes} -\label{sec:cls-function} - -\begin{verbatim} -class Function$\,n$[a$_1$, ..., a$_n$,b] with { - // some methods in Any are overwritten - def apply(x$_1$: a$_1$, ..., x$_n$: a$_n$): b -} -\end{verbatim} -Class \verb@Function1@ additionally defines the method -\begin{verbatim} - def o [c] (f: Function1[c,a$_1$]): Function1[c,b] = x: c => apply(f(x)) -\end{verbatim} -There is also a module \verb@Function@, defined as follows. -\begin{verbatim} -module Function { - def compose[a](fs: List[(a)a]): (a)a = { - x => fs match { - case Nil => x - case f :: fs1 => compose(fs1)(f(x)) - } - } -} -\end{verbatim} -A subclass of \verb@Function$\,n$@ describes partial functions, which -are undefined on some points in their domain. - -\begin{verbatim} -class PartialFunction$\,n$[a$_1$, ..., a$_n$,b] extends Function$\,n$[a$_1$, ..., a$_n$,b] with { - def isDefined(x$_1$: a$_1$, ..., x$_n$: a$_n$): Boolean -} -\end{verbatim} - -In addition to the \verb@apply@ method of functions, partial functions -also have a \verb@isDefined@ method, which tells whether the function -is defined at the given argument. - -Classes \verb@Function@ and \verb@PartialFunction@ are defined to be aliases for -\verb@Function1@ and \verb@PartialFunction1@: -\begin{verbatim} - type Function[a,b] = Function1[a,b] - type PartialFunction[a,b] = PartialFunction1[a,b] - def Function[a,b]: class Function1[a,b] = Function1[a,b] - def PartialFunction[a,b]: class PartialFunction1[a,b] = PartialFunction1[a,b] -\end{verbatim} - -\subsection{Class \prog{List}}\label{cls-list} - -\begin{verbatim} -abstract class List[a] with { - abstract def isEmpty: Boolean; - abstract def head: a; - abstract def tail: List[a]; - - def ::(x: a): List[a] = - new ::_class(x)(this); - - def :::(prefix: List[a]): List[a] = - if (prefix.isEmpty) this - else prefix.head :: (prefix.tail ::: this); - - def length: Int = { - this match { - case [] => 0 - case _ :: xs => xs.length + 1} - } -\end{verbatim} -\begin{verbatim} - def init: List[a] = - if (isEmpty) error("Nil.init") - else if (tail.isEmpty) Nil - else head :: tail.init; - - def last: a = - if (isEmpty) error("Nil.last") - else if (tail.isEmpty) head - else tail.last; - - def take(n: Int): List[a] = - if (n == 0) Nil - else head :: tail.take(n-1); - - def drop(n: Int): List[a] = - if (n == 0) this - else tail.drop(n-1); - - def takeWhile(p: (a)Boolean): List[a] = - if (isEmpty || !p(head)) Nil - else head :: tail.takeWhile(p); - - def dropWhile(p: (a)Boolean): List[a] = - if (isEmpty || !p(head)) this - else tail.dropWhile(p); - - def at(n: Int) = drop(n).head; -\end{verbatim} -\begin{verbatim} - def map[b](f: (a)b): List[b] = - if (isEmpty) Nil - else f(head) :: tail.map(f); - - def foreach(f: (a)Unit): Unit = - if (isEmpty) () - else (f(head); tail.foreach(f)); - - def filter(p: (a)Boolean): List[a] = - if (isEmpty) this - else if (p(head)) head :: tail.filter(p) - else tail.filter(p); - - def forall(p: (a)Boolean): Boolean = - isEmpty || (p(head) && tail.forall(p)); - - def exists(p: (a)Boolean): Boolean = - !isEmpty && (p(head) || tail.exists(p)); -\end{verbatim} -\begin{verbatim} - def :_foldl[b](z: b)(f: (b, a)b) = match { - case [] => z - case x :: xs => (f(z, x) :_foldl xs)(f) - } - - def foldr[b](z: b)(f: (a, b)b) = match { - case [] => z - case x :: xs => f(x, (xs foldr z)(f)) - } - - def redl(f: (a, a)a) = match { - case [] => error("redl of empty list") - case x :: xs => (x :_foldl xs)(f) - } - - def redr(f: (a, a)a): a = match { - case [] => error("redr of empty list") - case [x] => x - case x :: xs => f(x, xs redr f) - } -\end{verbatim} -\begin{verbatim} - def flatMap[b](f: (a)List[b]): List[b] = - if (isEmpty) Nil - else f(head) ::: tail.flatMap(f); - - def reverse: List[a] = { - def snoc(xs: List[a], x: a): List[a] = x :: xs; - fold(snoc)(Nil) - } - - def print: Unit = - if (isEmpty) System.out.println("[]") - else { - System.out.print(head.as[java.lang.Object]); - System.out.print(" :: "); - tail.print - } - - def toArray: Array[a] = { - val xs = new Array[a](length); - copyToArray(xs, 0); - xs - } - - def copyToArray(xs: Array[a], start: Int): Int = { - xs(start) = head; - tail.copyToArray(xs, start + 1) - } -\end{verbatim} -\begin{verbatim} - def mkString(start: String, sep: String, end: String): String = - start + - (if (isEmpty) end - else if (tail.isEmpty) head.toString() + end - else head.toString().concat(sep).concat(tail.mkString("", sep, end))); - - def zip[b](that: List[b]): List[(a,b)] = - if (this.isEmpty || that.isEmpty) Nil - else (this.head, that.head) :: this.tail.zip(that.tail); -\end{verbatim} -\begin{verbatim} - def contains(elem: a) = exists(x => x == elem); - - def union(that: List[a]): List[a] = - if (this.isEmpty) that - else { - val result = this.tail union that; - if (that contains this.head) result else this.head :: result; - } - - def diff(that: List[a]): List[a] = - if (that.isEmpty) this - else { - val result = this.tail diff that; - if (that contains this.head) result else this.head :: result; - } - - def intersect(that: List[a]): List[a] = filter(x => that contains x); - - def removeDuplicates: List[a] = - if (isEmpty) this - else { - val rest = tail.removeDuplicates; - if (rest contains head) rest else head :: rest - } -} -\end{verbatim} -\begin{verbatim} -final case class ::_class[b](hd: b)(tl: List[b]) extends List[b] with { - def isEmpty = False; - def head = hd; - def tail = tl; - override def toString(): String = mkString("[", ",", "]"); -} -\end{verbatim} -\begin{verbatim} -final case class Nil[c] extends List[c] with { - def isEmpty = True; - def head: c = error("head of empty list"); - def tail: List[c] = error("tail of empty list"); - override def toString(): String = "[]"; -} -\end{verbatim} - -\subsection{Class \prog{Array}} - -The class of generic arrays is defined as follows. - -\begin{verbatim} -class Array[a](l: int) extends Function[Int, a] with { - def length: int = l - def apply(i: Int): a = ... - def update(i: Int)(x: a): Unit = ... -} -\end{verbatim} -\comment{ -\begin{verbatim} -module Array { - def create[a](i1: Int): Array[a] = Array[a](i1) - def create[a](i1: Int, i2: Int): Array[Array[a]] = { - val x: Array[Array[a]] = create(i1) - 0 to (i1 - 1) do { i => x(i) = create(i2) } - x - } - ... - def create[a](i1: Int, i2: Int, i3: Int, i4: Int, i5: Int, - i6: Int, i7: Int, i8: Int, i9: Int, i10: Int) - : Array[Array[Array[Array[Array[Array[Array[Array[Array[Array[a]]]]]]]]]] = { - val x: Array[Array[Array[Array[Array[Array[Array[Array[Array[a]]]]]]]]] = create(i1) - 0 to (i1 - 1) do { i => x(i) = create(i2, i3, i4, i5, i6, i7, i8, i9, i10) } - x - } -} -\end{verbatim} -} -\section{Exceptions} -\label{sec:exceptions} - -There is a predefined type \verb@Throwable@, as well as functions to -throw and handle values of type \verb@Throwable@. These are declared -as follows. - -\begin{verbatim} - class Throwable with { - def throw[a]: a - } - class ExceptOrFinally[a] with { - def except (handler: PartialFunction[Throwable,a]): a - def finally (def handler: Unit): a - } - def try [a] (def body: a): ExceptOrFinally[a] -\end{verbatim} - -The type \verb@Throwable@ represents exceptions and error objects; it -may be identified with an analogous type of the underlying -implementation such as \verb@java.lang.Throwable@. We will in the -following loosely call values of type \verb@Throwable@ exceptions. - -The \verb@throw@ method in \verb@Throwable@ aborts execution of the -thread executing it and passes the thrown exception to the handler -that was most recently installed by a -\verb@try@ function in the current thread. If no \verb@try@ method is -active, the thread terminates. - -The \verb@try@ function executes its body with the given exception -handler. A \verb@try@ expression comes in two forms. The first form is - -\begin{verbatim} -try $body$ except $handler$ . -\end{verbatim} - -If $body$ executes without an exception being thrown, then executing -the try expression is equivalent to just executing $body$. If some -exception is thrown from within $body$ for which \verb@handler@ is defined, -the handler is invoked with the thrown exception as argument. - -The second form of a try expression is - -\begin{verbatim} -try $body$ finally $handler$ . -\end{verbatim} - -This expression will execute $body$. A normal execution of $body$ is -followed by an invocation of the $handler$ expression. The $handler$ -expression does not take arguments and has \verb@Unit@ as result type. -If execution of the handler expression throws an exception, this -exception is propagated out of the \verb@try@ statement. Otherwise, -if an exception was thrown in $body$ prior to invocation of $handler$, -that exception is re-thrown after the invocation. Finally, if both -$body$ and $handler$ terminate normally, the original result of -$body$ is the result of the \verb@try@ expression. - -\example An example of a try-except expression: - -\begin{verbatim} -try { - System.in.readString() -} except { - case ex: EndOfFile => "" -} -\end{verbatim} - -\example An example of a try-finally expression: - -\begin{verbatim} -file = open (fileName) -if (file != null) { - try { - process (file) - } finally { - file.close - } -} -\end{verbatim} - -\section{Concurrency} -\label{sec:concurrency} - -\subsection{Basic Concurrency Constructs} - -Scala programs may be executed by several threads that operate -concurrently. The thread model used is based on the model of the -underlying run-time system. We postulate a predefined -class \verb@Thread@ for run-time threads, -\verb@fork@ function to spawn off a new thread, -as well as \verb@Monitor@ and \verb@Signal@ classes. These are -specified as follows\nyi{Concurrentcy constructs are}. - - -\begin{verbatim} -class Thread with { ... } -def fork (def p: Unit): Thread -\end{verbatim} - -The \verb@fork@ function runs its argument computation \verb@p@ in a -separate thread. It returns the thread object immediately to its -caller. Unhandled exceptions (\sref{sec:exceptions}) thrown during -evaluation of \verb@p@ abort execution of the forked thread and are -otherwise ignored. - -\begin{verbatim} -class Monitor with { - def synchronized [a] (def e: a): a -} -\end{verbatim} - -Monitors define a \verb@synchronized@ method which provides mutual -exclusion between threads. It executes its argument computation -\verb@e@ while asserting exclusive ownership of the monitor -object whose method is invoked. If some other thread has ownership of -the same monitor object, the computation is delayed until the other -process has relinquished its ownership. Ownership of a monitor is -relinquished at the end of the argument computation, and while the -computation is waiting for a signal. - -\begin{verbatim} -class Signal with { - def wait: Unit - def wait(msec: Long): Unit - def notify: Unit - def notifyAll: Unit -} -\end{verbatim} - -The \verb@Signal@ class provides the basic means for process -synchronization. The \verb@wait@ method of a signal suspends the -calling thread until it is woken up by some future invocation of the -signal's \verb@notify@ or \verb@notifyAll@ method. The \verb@notify@ -method wakes up one thread that is waiting for the signal. The -\verb@notifyAll@ method wakes up all threads that are waiting for the -signal. A second version of the \verb@wait@ method takes a time-out -parameter (given in milliseconds). A thread calling \verb@wait(msec)@ -will suspend until unblocked by a \verb@notify@ or \verb@notifyAll@ -method, or until the \verb@msec@ millseconds have passed. - -\subsection{Channels} - -\begin{verbatim} -class Channel[a] with { - def write(x: a): Unit - def read: a -} -\end{verbatim} - -An object of type \verb@Channel[a]@ Channels offer a write-operation -which writes data of type \verb@a@ to the channel, and a read -operation, which returns written data as a result. The write operation -is non-blocking; that is it returns immediately without waiting for -the written data to be read. - -\subsection{Message Spaces} - -The Scala library also provides message spaces as a higher-level, -flexible construct for process synchronization and communication. A -{\em message} is an arbitrary object that inherits from the -\verb@Message@ class. -There is a special message \verb@TIMEOUT@ which is used to signal a time-out. -\begin{verbatim} -class Message -case class TIMEOUT extends Message -\end{verbatim} -Message spaces implement the following class. -\begin{verbatim} -class MessageSpace with { - def send(msg: Message): Unit - def receive[a](f: PartialFunction1[Message, a]): a - def receiveWithin[a](msec: Long)(f: PartialFunction1[Message, a]): a -} -\end{verbatim} -The state of a message space consists of a multi-set of messages. -Messages are added to the space using the \verb@send@ method. Messages -are removed using the \verb@receive@ method, which is passed a message -processor \verb@f@ as argument, which is a partial function from -messages to some arbitrary result type. Typically, this function is -implemented as a pattern matching expression. The \verb@receive@ -method blocks until there is a message in the space for which its -message processor is defined. The matching message is then removed -from the space and the blocked thread is restarted by applying the -message processor to the message. Both sent messages and receivers are -ordered in time. A receiver $r$ is applied to a matching message $m$ -only if there is no other (message, receiver) pair which precedes $(m, -r)$ in the partial ordering on pairs that orders each component in -time. - -The message space class also offers a method \verb@receiveWithin@ -which blocks for only a specified maximal amount of time. If no -message is received within the specified time interval (given in -milliseconds), the message processor argument $f$ will be unblocked -with the special \verb@TIMEOUT@ message. - -\appendix -\chapter{Scala Syntax Summary} - -The lexical syntax of Scala is given by the following grammar in EBNF -form. - -\begin{verbatim} - upper \=::= \=`A' | ... | `Z' | `$\Dollar$' | `_' - lower \>::= \>`a' | ... | `z' - letter \>::= \>upper | lower - digit \>::= \>`0' | ... | `9' - special \>::= \>``everything else except parentheses ([{}]) and period'' - - op \>::= \>special {special} [`_' [id]] - varid \>::= \>lower {letter | digit} [`_' [id]] - id \>::= \>upper {letter | digit} [`_' [id]] - \> |\>varid - \> |\>op - - intLit \>::= \>``as in Java'' - floatLit \>::= \>``as in Java'' - charLit \>::= \>``as in Java'' - stringLit \>::= \>``as in Java'' - - comment \>::= \>`/*' ``any sequence of characters'' `*/' - \> |\>`//' `any sequence of characters up to end of line'' -\end{verbatim} - -The context-free syntax of Scala is given by the following EBNF -grammar. - -\begin{verbatim} - literal \=::= \= intLit - \> |\> floatLit - \> |\> charLit - \> |\> stringLit - \> |\> symbolLit -\end{verbatim} - -\begin{verbatim} - StableId \=::= \= id - \> |\> Path `.' id - Path \>::=\> StableId - \> |\> [id `.'] this - \> |\> [id '.'] super [`[' id `]']`.' id - - Type \>::= \> Type1 `=>' Type - \> |\> `(' [Types] `)' `=>' Type - \> |\> Type1 - Type1 \>::= \> SimpleType {with SimpleType} [Refinement] - SimpleType \>::= \> SimpleType TypeArgs - \> |\> SimpleType `#' id - \> |\> StableId - \> |\> Path `.' type - \> |\> `(' Type ')' - TypeArgs \>::= \> `[' Types `]' - Types \>::= \> Type {`,' Type} - Refinement \>::=\> `{' [RefineStat {`;' RefineStat}] `}' - RefineStat \>::=\> Dcl - \> |\> type TypeDef {`,' TypeDef} - \> |\> - - Exprs \>::=\> Expr {`,' Expr} - Expr \>::=\> [Bindings `=>'] Expr - \> |\> if `(' Expr `)' Expr [[`;'] else Expr] - \> |\> try `{' block `}' [catch Expr] [finally Expr] - \> |\> do Expr [`;'] while `(' Expr ')' - \> |\> for `(' Enumerators `)' (do | yield) Expr - \> |\> [SimpleExpr `.'] id `=' Expr - \> |\> SimpleExpr ArgumentExpr `=' Expr - \> |\> PostfixExpr [`:' Type1] - PostfixExpr \>::=\> InfixExpr [id] - InfixExpr \>::=\> PrefixExpr - \> |\> InfixExpr id InfixExpr - PrefixExpr \>::=\> [`-' | `+' | `~' | `!'] SimpleExpr - SimpleExpr \>::=\> literal - \> |\> true - \> |\> false - \> |\> null - \> |\> Path - \> |\> `(' [Expr] `)' - \> |\> BlockExpr - \> |\> new Template - \> |\> SimpleExpr `.' id - \> |\> id `#' id - \> |\> SimpleExpr TypeArgs - \> |\> SimpleExpr ArgumentExpr - ArgumentExpr \>::=\> `(' Expr ')' - \> |\> BlockExpr - BlockExpr \>::=\> `{' CaseClause {CaseClause} `}' - \> |\> `{' Block `}' - Block \>::=\> {BlockStat `;'} [Expr] -\end{verbatim} - -\begin{verbatim} - Enumerators \=::= \= Generator {`;' Enumerator} - Enumerator \>::=\> Generator - \> |\> Expr - Generator \>::=\> val Pattern `<-' Expr - Block \>::=\> {BlockStat `;'} [Expr] - BlockStat \>::=\> Import - \> |\> Def - \> |\> {LocalModifier} ClsDef - \> |\> Expr - \> |\> - - CaseClause \>::=\> case Pattern [`if' PostfixExpr] `=>' Block - - Constr \>::=\> StableId [TypeArgs] [`(' [Exprs] `)'] - - Pattern \>::= \= TreePattern { `|' TreePattern } - - TreePattern \>::= \> varid `:' Type - \> | \> `_' `:' Type - \> | \> SimplePattern [ '*' | '?' | '+' ] - \> | \> SimplePattern { id SimplePattern } - - SimplePattern \>::= \> varid [ '@' SimplePattern ] - \> | \> `_' - \> | \> literal - \> | \> StableId [ `(' [Patterns] `)' ] - \> | \> `(' Patterns `)' - \> | \> - - Patterns \>::= \> Pattern {`,' Pattern} - - TypeParamClause \>::=\> `[' TypeParam {`,' TypeParam} `]' - FunTypeParamClause \>::=\> `[' TypeDcl {`,' TypeDcl} `]' - TypeParam \>::=\> [`+' | `-'] TypeDcl - ParamClause \>::=\> `(' [Param {`,' Param}] `)' - Param \>::=\> [def] id `:' Type [`*'] - Bindings \>::=\> id [`:' Type1] - \> |\> `(' Binding {`,' Binding `)' - Binding \>::=\> id [`:' Type] - - Modifier \>::=\> LocalModifier - \> |\> private - \> |\> protected - \> |\> override - LocalModifier \>::=\> abstract - \> |\> final - \> |\> sealed - - Template \>::=\> Constr {`with' Constr} [TemplateBody] - TemplateBody \>::=\> `{' [TemplateStat {`;' TemplateStat}] `}' -\end{verbatim} -\begin{verbatim} - TemplateStat \=::= \= Import - \> |\> {Modifier} Def - \> |\> {Modifier} Dcl - \> |\> Expr - \> |\> - - Import \>::=\> import ImportExpr {`,' ImportExpr} - ImportExpr \>::=\> StableId `.' (id | `_' | ImportSelectors) - ImportSelectors \>::=\> `{' {ImportSelector `,'} (ImportSelector | `_') `}' - ImportSelector \>::=\> id [`=>' id | `=>' `_'] - - Dcl \>::=\> val ValDcl {`,' ValDcl} - \> |\> var VarDcl {`,' VarDcl} - \> |\> def FunDcl {`,' FunDcl} - \> |\> type TypeDcl {`,' TypeDcl} - ValDcl \>::=\> id `:' Type - VarDcl \>::=\> id `:' Type - FunDcl \>::=\> id [FunTypeParamClause] {ParamClause} `:' Type - TypeDcl \>::=\> id [`>:' Type] [`<:' Type] - - Def \>::=\> val PatDef {`,' PatDef} - \> |\> var VarDef {`,' VarDef} - \> |\> def FunDef {`,' FunDef} - \> |\> type TypeDef {`,' TypeDef} - \> |\> ClsDef - PatDef \>::=\> Pattern `=' Expr - VarDef \>::=\> id [`:' Type] `=' Expr - \> |\> id `:' Type `=' `_' - FunDef \>::=\> id [FunTypeParamClause] {ParamClause} [`:' Type] `=' Expr - | this ParamClause `=' ConstrExpr - TypeDef \>::=\> id [TypeParamClause] `=' Type - ClsDef \>::=\> ([case] class | trait) ClassDef {`,' ClassDef} - \> |\> [case] object ObjectDef {`,' ObjectDef} - ClassDef \>::=\> id [TypeParamClause] [ParamClause] [`:' SimpleType] ClassTemplate - ObjectDef \>::=\> id [`:' SimpleType] ClassTemplate - ClassTemplate \>::=\> extends Template - \> |\> TemplateBody - \> |\> - ConstrExpr \>::=\> this ArgumentExpr - \> |\> `{' {BlockStat `;'} this ArgumentExpr {`;' BlockStat} `}' - - CompilationUnit \>::=\> [package QualId `;'] {TopStat `;'} TopStat - TopStat \>::=\> {Modifier} ClsDef - \> |\> Import - \> |\> Packaging - \> |\> - Packaging \>::=\> package QualId `{' {TopStat `;'} TopStat `}' - QualId \>::=\> id {`.' id} -\end{verbatim} - -case class extends { ... } - -trait List { } -class Nil -class Cons - -\comment{changes: - Type \=::= \= SimpleType {with SimpleType} [with Refinement] - \> |\> class SimpleType - SimpleType \>::=\> SimpleType [TypeArgs] - \> |\> `(' [Types] `)' - \> |\> - \> |\> this -} -\end{document} - -\comment{changes: - - Type \=::= \= SimpleType {with SimpleType} [with Refinement] - \> |\> class SimpleType - SimpleType \>::=\> TypeDesignator [TypeArgs] - \> |\> `(' Type `,' Types `)' - \> |\> `(' [Types] `)' Type - \> |\> this - - PureDef \>::=\> module ModuleDef {`,' ModuleDef} - \>::=\> def FunDef {`,' FunDef} - \> |\> type TypeDef {`,' TypeDef} - \> |\> [case] class ClassDef {`,' ClassDef} - \> |\> case CaseDef {`,' CaseDef} - CaseDef \>::=\> Ids ClassTemplate - - Modifier \>::=\> final - \> |\> private - \> |\> protected - \> |\> override [QualId] - \> |\> qualified - \> |\> abstract - -\section{Class Aliases} -\label{sec:class-alias} - -\syntax\begin{verbatim} - ClassDef \=::= \= ClassAlias - InterfaceDef \>::= \> ClassAlias - ClassAlias \>::= \> id [TypeParamClause] `=' SimpleType -\end{verbatim} - -Classes may also be defined to be aliases for other classes. A class -alias is of the form $\CLASS;c[tps] = d[targs]$ where $d[targs]$ is a -class type. Both $tps$ and $targs$ may be empty. -This introduces the type $c[tps]$ as an alias for type -$d[targs]$, in the same way the following type alias definition would: -\begin{verbatim} -type c[tps] = d[targs] -\end{verbatim} -The class alias definition is legal if the type alias definition would be legal. - -Assuming $d$ defines a class with type parameters $tps'$ and -parameters $(ps_1) \ldots (ps_n)$, the newly defined type is also -introduced as a class with a constructor which takes type parameters -$[tps]$, and which takes value parameters -$([targs/tps']ps_1)\ldots([targs/tps']ps_n)$. - -The modifiers \verb@private@ and -\verb@protected@ apply to a class alias independently of the class it represents. -The class $c$ is regarded as final if $d$ is final, or if a -\verb@final@ modifier is given for the alias definition. -$c$ is regarded as a case class iff $d$ is one. In this -case, -\begin{itemize} -\item the alias definition may also be prefixed with \verb@case@, and -\item the case constructor is also aliased, as if it was -defined such: -\begin{verbatim} -def c[tps](ps$_1$)\ldots(ps$_n$):D = d[targs]$([targs/tps']ps$_1$)\ldots([targs/tps']ps$_n$)$ . -\end{verbatim} -The new function $c$ is again classified as a case constructor, so -it may appear in constructor patterns (\sref{sec:patterns}). -\end{itemize} -Aliases for interfaces follow the same rules as class aliases, but -start with \verb@interface@ instead of \verb@class@. -} - -type T extends { ... } - -class C extends { ... } - -new C { ... } - -type C -class C < { ... } - -A & B & C & -\ifqualified{ -Parameter clauses (\sref{sec:funsigs}), -definitions that are local to a block (\sref{sec:blocks}), and import -clauses always introduce {\em simple names} $x$, which consist of a -single identifier. On the other hand, definitions and declarations -that form part of a module (\sref{sec:modules}) or a class -(\sref{sec:classes}) conceptually always introduce {\em qualified -names}\nyi{Qualified names are} -$Q\qex x$ where a simple name $x$ comes with a qualified -identifier $Q$. $Q$ is either the fully qualified name of a module or -class which is labelled -\verb@qualified@, or it is the empty name $\epsilon$. - -The {\em fully qualified name} of a module or class $M[targs]$ with -simple name $M$ and type arguments $[targs]$ is -\begin{itemize} -\item $Q.M$, if the definition of $M$ appears in the template defining -a module or class with fully qualified name $Q$. -\item -$M$ if the definition of $M$ appears on the top-level or as a definition -in a block. -\end{itemize} -} - -\ifqualified{ -It is possible that a definition in some class or module $M$ -introduces several qualified names $Q_1\qex x \commadots Q_n\qex x$ in a name -space that have the same simple name suffix but different qualifiers -$Q_1 \commadots Q_n$. This happens for instance if a module \verb@M@ -implements two qualified classes \verb@C@, \verb@D@ that each define a -function \verb@f@: -\begin{verbatim} -qualified abstract class B { def f: Unit = ""} -qualified abstract class C extends B { def f: Unit } -qualified abstract class D extends B { def f: Unit } - -module M extends C with D with { - override C def f = println("C::f") - override D def f = println("D::f") - \= - // f \>// error: ambiguous - (this:D).f \>// prints ``D::f'' -} - -def main() = (M:C).f \>// prints ``C::f'' -\end{verbatim} -Members of modules or classes are accessed using simple names, -not qualified names. - -The {\em qualified expansion} of a simple name $x$ in some type $T$ is -determined as follows: Let $Q_1\qex x \commadots Q_n\qex x$ be all the -qualified names of members of $T$ that have a simple name suffix $x$. -If one of the qualifiers $Q_i$ is the empty name $\epsilon$, then the -qualified expansion of $x$ in $T$ is $\epsilon\qex x$. Otherwise, let -$C_1 -\commadots C_n$ be the base classes (\sref{sec:base-classes}) -of $T$ that have fully qualified -names $Q_1 -\commadots Q_n$, respectively. If there exists a least class $C_j$ -among the $C_i$ in the subclass ordering, then the qualified expansion -of $x$ in $T$ is $Q_j\qex x$. Otherwise the qualified expansion does not -exist. - -Conversely, if $Q\qex x$ is the qualified expansion of some simple -name $x$ in $M$, we say that the entity named $Q\qex x$ in $M$ is {\em -identified in $M$ by the simple name} $x$. We leave out the -qualification ``in $M$'' if it is clear from the context. -In the example above, the qualified expansion of \verb@f@ in \verb@C@ -is \verb@C::f@, because \verb@C@ is a subclass of \verb@B@. On the -other hand, the qualified expansion of \verb@f@ in \verb@M@ does not -exist, since among the two choices \verb@C::f@ and \verb@D::f@ neither -class is a subclass of the other. - -A member access $e.x$ of some type term $e$ of type $T$ references the -member identified in $T$ by the simple name $x$ (i.e.\ the member -which is named by the qualified expansion of $x$ in $T$). - -In the example above, the simple name \verb@f@ in \verb@M@ would be -ambiguous since the qualified expansion of \verb@f@ in \verb@M@ does -not exist. To reference one of the two functions with simple name -\verb@f@, one can use an explicit typing. For instance, the name -\verb@(this:D).f@ references the implementation of \verb@D::f@ in -\verb@M@. -} - -\comment{ -\example The following example illustrates the difference between -virtual and non-virtual members with respect to overriding. - -\begin{verbatim} -class C with { - virtual def f = "f in C" - def g = "g in C" - def both1 = this.f ++ ", " ++ this.g - def both2 = f ++ ", " ++ g -} - -class D extends C with { - override def f = "f in D" - override def g = "redefined g in D" - new def g = "new g in D" -} - -val d = D -println(d.f) \=// prints ``f in D'' -println(d.g) \>// prints ``new g in D'' -println(d.both1) \>// prints ``f in D, redefined g in D'' -println(d.both2) \>// prints ``f in D, g in C'' - -val c: C = d -println(c.f) \=// prints ``f in D'' -println(c.g) \>// prints ``redefined g in D'' -println(c.both1) \>// prints ``f in D, redefined g in D'' -println(c.both2) \>// prints ``f in D, g in C'' -\end{verbatim} -} - -\comment{ -\section{The Self Type} -\label{sec:self-type} - -\syntax\begin{verbatim} -SimpleType \=::= \= $\This$ -\end{verbatim} - -The self type \verb@this@ may be used in the statement part of a -template, where it refers to the type of the object being defined by -the template. It is the type of the self reference \verb@this@. - -For every leaf class (\sref{sec:modifiers}) $C$, \verb@this@ is -treated as an alias for the class itself, as if it was declared such: -\begin{verbatim} -final class C ... with { - type this = C - ... -} -\end{verbatim} -For non-leaf classes $C$, \verb@this@ is treated as an abstract type -bounded by the class itself, as if it was declared such: -\begin{verbatim} -abstract class C ... with { - type this extends C - ... -} -\end{verbatim} - -Analogously, for every compound type \verb@$T_1$ with ... with $T_n$@, -\verb@this@ is treated as an abstract type conforming to the whole compound -type, as if it was bound in the refinement -\begin{verbatim} -type this extends $T_1$ with ... with $T_n$ . -\end{verbatim} -Finally, for every declaration of a parameter or abstract type -\mbox{$a \extends T$}, \verb@this@ is treated as an an abstract type -conforming to $a$, as if the bound type $T$ was augmented to -\verb@$T$ with { abstract type this extends $a$ }@. -On the other hand, if the parameter or abstract type is declared -\verb@final@, as in $\FINAL;a \extends T$, then \verb@this@ is treated as an alias -for $a$, as if the bound type $T$ was augmented to -\verb@$T$ with { type this = $a$ }@. - -\example -Consider the following classes for one- and two-dimensional -points with a \verb@distance@ method that computes the distance -between two points of the same type. -\begin{verbatim} -class Point1D(x: Float) with { - def xCoord = x - def distance (that: this) = abs(this.xCoord - that.xCoord) - def self: this = this -} -final class FinalPoint1D(x: Float) extends Point1D(x) - -class Point2D(x: Float, y: Float) extends Point1D(x) with { - def yCoord = y - override def distance(that: this) = - sqrt (square(this.xCoord - that.xCoord) + square(this.yCoord - that.yCoord)) -} -\end{verbatim} -Assume the following definitions: -\begin{verbatim} -val p1f: FinalPoint1D = FinalPoint1D(0.0) -val p1a: Point1D = p1f -val p1b: Point1D = Point2D(3.0, 4.0) -\end{verbatim} -Of the following expressions, three are well-formed, the other three -are ill-formed. -\begin{verbatim} -p1f distance p1f \=// OK, yields 0,0 -p1f distance p1b \>// OK, yields 3.0 -p1a distance p1a \>// OK, yields 0.0 -p1a distance p1f \>// ERROR, required: p1a.this, found: FinalPoint1D -p1a distance p1b \>// ERROR, required: p1a.this, found: p1b.this -p1b distance p1a \>// ERROR, required: p1b.this, found: p1a.this -\end{verbatim} -The last of these expressions would cause an illegal access to a -non-existing class \verb@yCoord@ of an object of type \verb@Point1D@, -if it were permitted to execute in spite of being not well-typed. -} - -\iflet{ -\section{Let Definitions} -\label{sec:letdef} - -\syntax\begin{verbatim} - PureDef \=::= \= $\LET$ ValDef {`,' ValDef} - ValDef \>::= \> id [`:' Type] `=' Expr -\end{verbatim} - -A let definition $\LET;x: T = e$ defines $x$ as a name of the value -that results from the delayed evaluation of $e$. The type $T$ must be -a concrete value type (\sref{sec:types}) and the type of the -expression $e$ must conform to $T$. The effect of the let definition -is to bind the left-hand side $x$ to the result of evaluating $e$ -converted to type $T$. However, the expression $e$ is not evaluated -at the point of the let definition, but is instead evaluated the first -time $x$ is dereferenced during execution of the program (which might -be never at all). An attempt to dereference $x$ again in the course of -evaluation of $e$ leads to a run-time error. Other threads trying to -dereference $x$ while $e$ is being evaluated block until evaluation is -complete. - -The type $T$ may be omitted if it can be determined using local type -inference (\sref{sec:local-type-inf}). -} - -\section{Packagings} - -\syntax\begin{verbatim} - Packaging \=::= \= package QualId `{' {TopStat `;'} TopStat `}' -\end{verbatim} - -A package is a special object which defines a set of member classes, -objects and packages. Unlike other objects, packages are not defined -by a definition. Instead, the set of members is determined by -packagings. - -A packaging \verb@package p { ds }@ injects all definitions in -\verb@ds@ as members into the package whose qualified name is -\verb@p@. If a definition in \verb@ds@ is labelled \verb@private@, it -is visible only for other members in the package. - -Selections \verb@p.m@ from \verb@p@ as well as imports from \verb@p@ -work as for objects. However, unlike other objects, packages may not -be used as values. It is illegal to have a package with the same fully -qualified name as an object or a class. - -Top-level definitions outside a packaging are assumed to be injected -into a special empty package. That package cannot be named and -therefore cannot be imported. However, members of the empty package -are visible to each other wihtout qualification. - -\example The following example will create a hello world program as -function \verb@main@ of module \verb@test.HelloWorld@. -\begin{verbatim} -package test; - -object HelloWord { - def main(args: Array[String]) = System.out.println("hello world") -} -\end{verbatim} - -\ifpackaging{ -Packagings augment top-level modules and classes. A simple packaging -$$\PACKAGE;id;\WITH;mi_1;\ldots;\WITH;mi_n;\WITH;(stats)$$ augments the -template of the top-level module or class named $id$ with new mixin -classes and with new member definitions. - -The static effect of such a packaging can be expressed as a -source-to-source tranformation which adds $mi_1 \commadots mi_n$ to -the mixin classes of $id$, and which adds the definitions in $stats$ -to the statement part of $id$'s template. Each type $mi_j$ must refer -to an interface type and $stats$ must consists only of pure and local -definitions. The augmented template and any class that extends it -must be well-formed. The aditional definitions may not overwrite -definitions of the augmented template, and they may not access private -members of it. - -Several packagings can be applied to the same top-level definition, -and those packagings may reside in different compilation units. - -A qualified packaging $\PACKAGE;Q.id;\WITH;t$ is equivalent to the -nested packagings -\begin{verbatim} -package $Q$ with { - package $id$ with $t$ -} -\end{verbatim} - -A packaging with type parameters $\PACKAGE;c[tps];\WITH;...$ applies to -a parameterized class $c$. The number of type parameters must equal -the number of type parameters of $c$, and every bound in $tps$ must -conform to the corresponding bound in the original definition of $c$. - -The augmented class has the type parameters given in its original -definition. If a parameter $a$ of an augmented class has a bound $T$ -which is a strict subtype of the corresponding bound in the original -class, $a \conforms T$ is taken as an {\em application condition} for -the packaging. That is, every time a member defined in the packaging -is accessed or a conformance between class $c$ and a mixin base class -of the packaging needs to be established, an (instantiation of) the -application condition is checked. An unvalidated application -condition constitutes a type error. \todo{Need to specify more -precisely when application conditions are checked} - -\example The following example will create a hello world program as -function \verb@main@ of module \verb@test.HelloWorld@. -\begin{verbatim} -package test with { - module HelloWord with { - def main(args: Array[String]) = out.println("hello world") - } -} -\end{verbatim} -This assumes there exists a top-level definition that defines a -\verb@test@ module, e.g.: -\begin{verbatim} -module test -\end{verbatim} - -\example The following packaging adds class \verb@Comparable@ -(\ref{ex:comparable}) as a mixin to class -\verb@scala.List@, provided the list elements are also comparable. -Every instance of \verb@List[$T$]@ will then implement -\verb@Comparable[List[$T$]]@ in the way it is defined in the -packaging. Each use of the added functionality for an instance type -\verb@List[$T$]@ requires that the application condition -\verb@T $<:$ Comparable@ is satisfied. -\begin{verbatim} -package scala.List[a extends Comparable[a]] with Comparable[List[a]] with { - def < (that: List[a]) = (this, that) match { - case (_, Nil) => False - case (Nil, _) => True - case (x :: xs, y :: ys) => (x < y) || (x == y && xs < ys) - } -} -\end{verbatim} -} |