2016-07-25 21 views
1

に形質に共通の動作を抽象化、私は次のことを行い形質を持っています具体的な実装は次のようになります:Scalaの

class StringTrait extends MyTrait[String] { 
    def doSomething(elems: Seq[String]) = { 
    // some generic logic here 
    // some specific logic here (this code bit depends on the type of implementation) 
    // some generic logic here 
    } 
} 

私は今、どのようにStringTraitを渡すことができますか抽象クラスで定義されたジェネリックロジックを持つことができますか? 1つの方法は、サンクとして振る舞いを渡すことですが、それは私がdoSomething(...)メソッドを変更して、避けたい追加のパラメータを取らなければならないということです。

答えて

0

いくつかのオプションがありますが、説明のためにタイプ固有の動作がSeq [T] => Tであると仮定します(つまり、シーケンスをTとし、結果としてTを生成します)。ベース

継承:

trait MyTrait[T] { 
    def doTypeSpecificStuff(a: Seq[T]): T 

    def doSomething(elems: Seq[T]): T = { 
    // generic code stuff 
    val t: T = doTypeSpecificStuff(elems) 
    // more generic code 
    t 
    } 
} 

class StringTrait extends MyTrait[String] { 
    def doTypeSpecificStuff(elems: Seq[String]) = { 
    elems.reduceOption(_ + _).getOrElse("") 
    } 
} 

def client(thing: MyTrait[String], elems: Seq[String]) { 
    thing.doSomething(elems) 
} 

Typeクラス:

trait MyTypeClass[T] { 
    def doTypeSpecificStuff(a: Seq[T]): T 
} 

object StringTypeClass { 
    implicit val instance: StringTypeClass = new StringTypeClass() 
} 

class StringTypeClass extends MyTypeClass[String] { 
    def doTypeSpecificStuff(elems: Seq[String]): String = { 
    elems.reduceOption(_ + _).getOrElse("") 
    } 
} 

object TypeClassDependentBehaviour { 
    def doSomething[T](elems: Seq[T])(implicit tp: MyTypeClass[T]): T ={ 
    //some code 
    val stuff: T = tp.doTypeSpecificStuff(elems) 
    //more generic code 
    stuff 
    } 
} 

def client(elems: Seq[String]) { 
    TypeClassDependentBehaviour.doSomething(elems) 
}