2013-06-17 6 views
5

Sınıflarda bir desen eşleştirmesi yapmam gerekiyor. Sorun, bir Uzun ile eşleşen bazı Sorunlarım var.Scala: Scala: Modelin nasıl eşleştirileceği.Long ve java.lang.Long

Aynı şekilde scala.Long ve java.lang.Long işlemlerini yapmam gerekiyor, ancak neden her ikisini de neden beyan etmem gerekiyor?

def test(typ: Class[_]) { 
    typ match { 
     case q if q == classOf[Long] => println("scala long...") 
    } 
    } 

    val scalaLongField: java.reflect.Field = ...... 
    val javaLongField: java.reflect.Field = ...... 
    test(scalaLongField.getType) // prints "scala long..." 
    test(javaLongField.getType) // scala.MatchError: class java.lang.Long (of class java.lang.Class) 

bir örneğini ama sadece sınıf kalmadan hepsine aynı işlemek için bir yolu var mı: İşte

örneğidir? O hemen çalışmalıdır

cevap

3

nedeni java.lang.Long ve Long farklı sınıflar olmasıdır. Java'da, java.lang.Long.class ve Long.TYPE arasında bir fark vardır. Benzer şekilde, Scala'da, classOf[Long] ve classOf[java.lang.Long] farklıdır. Eğer sınıflar üzerinde desen maçı istiyorsanız

, sen helper bunun için unapply yöntemleri oluşturabilirsiniz:

object ScalaLong { 
    // Internal helper: 
    private def matchClass[T](c: Class[_], as: Class[T]): Option[Class[T]] = 
    if (as.isAssignableFrom(c)) Some(as) 
    else None; 

    // Matches wrapped Long classes. 
    object LongObject { 
    def unapply(c: Class[_]): Option[Class[java.lang.Long]] = 
     matchClass(c, classOf[java.lang.Long]); 
    } 
    // Matches primitive long classes. 
    object LongPrim { 
    def unapply(c: Class[_]): Option[Class[Long]] = 
     matchClass(c, classOf[Long]); 
    } 

    // -- Test: 

    def check(clz: Class[_]) = 
    clz match { 
     case LongPrim(c) => println("Long primitive: " + c); 
     case LongObject(c) => println("Long object: " + c); 
     case _    => println("Other: " + clz); 
    } 


    class Example { 
    val l1: scala.Long = 1L; 
    val l2: java.lang.Long = 1L; 
    val l3: java.lang.Integer = 1; 
    } 

    def main(argv: Array[String]) { 
    for(name <- Seq("l1", "l2", "l3")) 
     check(classOf[Example].getMethod(name).getReturnType()); 
    } 
} 

Genellikle, ayrı ayrı classOf[Long] ve classOf[java.lang.Long] tedavi etmek gerekir. Belki, onlarla ne yapmanız gerektiğini anlatırsanız, özel göreviniz için daha iyi bir çözüm bulabiliriz.

4

:

object LongTest { 
    def test(value: Any): Boolean = value match { 
    case l: Long => true 
    case _ => false 
    } 

    def run() { 
    println(test(1L)) 
    println(test(new java.lang.Long(1L))) 
    } 
} 

LongTest.run() // true and true 

Size yerine örneğinin sınıfları eşleştirmek istediğiniz bu bana belli değildi. Gerçekten ne istediğini anladığımdan emin değilim. Bunun gibi?

object LongTest { 
    def test(clazz: Class[_]): Boolean = 
    clazz == classOf[Long] || clazz == classOf[java.lang.Long] 

    def run() { 
    println(test(1L.getClass)) 
    println(test(new java.lang.Long(1L).getClass)) 
    } 
} 

LongTest.run() // true and true 

Veya bir desen eşleme olarak

:

def test(clazz: Class[_]): Boolean = clazz match { 
    case q if q == classOf[Long] || q == classOf[java.lang.Long] => true 
    case _ => false 
    } 
+0

Yalnızca değere sahip olduğumda! Buna sadece sınıfın olduğu zaman işe ihtiyacım var, dediğim gibi: "Bir örneği olmayan ama onları sadece sınıfla idare etmenin bir yolu var mı?" – maklemenz

+1

@mklemenz, örneklerinizi tam olarak ne istediğinizi kısıtlamak için iyi bir hizmet olurdu. Örnek yöntemlerin çoğunluğu (2/3) değere sahiptir, yalnızca bir tanesi yalnızca sınıfa sahiptir. –

+0

Soruyu düzenledim – maklemenz