2011-07-27 18 views
19

¿Hay alguna manera de forzar la precedencia del operador en Scala como lo hace en Haskell con $?

Por ejemplo, en Haskell, usted tiene:

a b c = ((a b) c) 

y

a $ b c = a (b c) 

¿Hay una manera similar a hacer esto en Scala? Sé que Scala no tiene operadores per se, pero ¿hay alguna manera de lograr un efecto similar?

Respuesta

15

infix vs. notación se utiliza a menudo de una manera similar a controlar la prioridad:

a b c d == a.b(c).d 
a.b c d == a.b.c(d) 
a b c.d == a.b(c.d) 

Scala también tiene un orden de precedencia fijo para los operadores utilizados en notación infija:

(all letters) 
| 
^ 
& 
< > 
= ! 
: 
+ - 
*/% 
(all other special characters) 

Nombres generalmente puede elegidos expresamente para tomar ventaja de esta . Por ejemplo, ~ y ^^ en la biblioteca de analizadores estándar.

+0

Perseguido de nuevo por el infractor fantasma que no deja explicación ... lo más extraño –

+1

precioso fragmento de código que el primero - lo tendré a mano para recordarme a mí mismo estas reglas. Gracias –

16

Es posible utilizar implícitos para lograr un efecto similar. Por ejemplo: (no probado, pero debería ser algo como esto)

object Operator { 

    class WithOperator[T](that: T) { 
    def &:[U](f: T => U) = f(that) 
    } 
    implicit def withOperator[T](that: T) = new WithOperator(that) 

} 

El uso de este sistema, no se puede utilizar el nombre $, porque el nombre tiene que terminar con un: (a fijar la asociatividad) y el dólar es un identificador normal (no el identificador del operador), por lo que no puede tenerlo en el mismo nombre que a:, a menos que los separe con guiones bajos.

Entonces, ¿cómo los usa? De esta manera:

val plusOne = (x: Int) => {x + 1} 
plusOne &: plusOne &: plusOne &: 1 
Cuestiones relacionadas