2010-10-29 11 views
6

necesito definir algunas clases de casos como el siguiente:cómo usar>< <= > = como funciones?

case class Gt(key: String, value: Any) extends Expression { 
    def evalute[V, E](f: String => Any) = { 
    def compare(v: Any): Boolean = { 
     v match { 
     case x: Number => x.doubleValue > value.asInstanceOf[Number].doubleValue 
     case x: Array[_] => x.forall(a => compare(a)) 
     case x => x.toString > value.toString 
     } 
    } 
    compare(f(key)) 
    } 
} 

no me gusta repetir que para> <> = y = <

también intenté esto:

trait Expression { 
    def evalute[V, E](f: String => Any) = true 

    def compare(v: Any, value: Any, cp: (Ordered[_], Ordered[_]) => Boolean): Boolean = { 
    v match { 
     case x: Number => cp(x.doubleValue, value.asInstanceOf[Number].doubleValue) 
     case x: Array[_] => x.forall(a => compare(a, value, cp)) 
     case x => cp(x.toString, value.toString) 
    } 
    } 
} 
case class Gt(key: String, value: Any) extends Expression { 
    def evalute[V, E](f: String => Any) = { 
    compare(f(key), value, ((a, b) => a > b)) 
    } 
} 

pero eso no funciona :(

error: could not find implicit value for parameter ord: scala.math.Ordering[scala.math.Ordered[_ >: _$1 with _$2]] 
compare(f(key), value, ((a, b) => a > b)) 

¿Hay alguna forma de pasar un operador como una función en Scala?

+0

¿Puede darnos una idea de * por qué * cree que necesita esa clase de caso? Es casi seguro que hay una solución mejor para lo que intenta lograr, pero es imposible saber qué es eso sin una idea de su escenario de uso previsto ... –

Respuesta

0

En Scala, esos no son los operadores, pero los métodos. Puede elevar cualquier método a una función colocando un guión bajo después de él. p.ej.

Welcome to Scala version 2.8.0.final (Java HotSpot(TM) Client VM, Java 1.6.0_21). 
Type in expressions to have them evaluated. 
Type :help for more information. 

scala> val f: (Int => Boolean) = 1 <= _ 
f: (Int) => Boolean = <function1> 

scala> (0 to 2).map(f) 
res0: scala.collection.immutable.IndexedSeq[Boolean] = Vector(false, true, true) 
+0

Sé que son métodos, pero parece que esos métodos (>, < , etc.) no se pueden pasar como parámetros, como los métodos normales – spacedragon

6

(a, b) => a > b funciona bien. Tu problema es con los tipos.

  1. ¿Cuáles son V y E en evalute[V, E] supone que es?

  2. Lo pasa (a, b) => a > b como el parámetro cp: (Ordered[_], Ordered[_]) => Boolean. Entonces tiene a: Ordered[_] y b: Ordered[_]. Que es lo mismo que a: Ordered[X] forSome {type X} y b: Ordered[Y] forSome {type Y}. Con estos tipos, a > b no tiene sentido.

+0

Sí, tiene razón. [V, E] son ​​inútiles aquí, olvidé eliminarlos. En realidad quiero comparar dos Cualquier valor en tiempo de ejecución, – spacedragon

+0

No se puede, porque 'Any' no se puede convertir a' Ordenado [Cualquiera] 'y'> 'es un método en 'Ordenado'. –

+0

Gracias. Recordaré la primera forma para cada operador. – spacedragon

Cuestiones relacionadas