2013-06-17 30 views
5

クラスでパターンマッチを行う必要があります。問題は、長い問題に合ったいくつかの問題があることです。Scala:scala.Longとjava.lang.Longのパターン一致方法

同じようにscala.Longとjava.lang.Longを処理する必要がありますが、なぜそれらの両方で宣言する必要がありますか?ここで

は一例です:

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) 

は、インスタンスが、単にクラスを持つことなく、それらを同じに扱う方法はありますか?それはすぐに動作するはず

答えて

3

理由はjava.lang.LongLongが異なるクラスであるということです。 Javaでは、java.lang.Long.classLong.TYPEの間に違いがあります。同様に、ScalaではclassOf[Long]classOf[java.lang.Long]が異なります。

あなたはクラス上のパターンマッチをしたい場合は、そのためのヘルパーメソッドunapply作成することができます。一般的に

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()); 
    } 
} 

を、あなたは別にclassOf[Long]classOf[java.lang.Long]を治療する必要があります。おそらく、あなたがそれらと何をしなければならないかを記述すれば、あなたの特定のタスクのためのより良い解決策を見つけることができます。

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 

あなたの代わりに、インスタンスのクラスを一致させたいという私には明らかではなかったです。私はあなたが実際に望んでいるものを理解しているか分からない。このような?

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 

やパターンマッチのように:

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

値がある場合のみ!私は、クラスを持っているときには、「インスタンスを持たずにクラスを処理する方法がありますか?」という質問のように、このクラスが必要です。 – maklemenz

+1

@mklemenzあなたは、あなたが望むものに正確にあなたの例を限定するのに十分役立つでしょう。サンプルメソッドの大部分(2/3)が値を持ちますが、クラスが1つしかありません。 –

+0

質問を編集しました – maklemenz

関連する問題