2011-11-16 10 views
2

問題を言葉で説明するのではなく、私が何をしたいのかを示すScalaインタープリタセッションを紹介しましょう。ALSOではサブクラスのみを受け入れるスケーラで構造型を入力する方法は?

scala> class A extends Parent{ 
     | def name = "Alex" 
     | } 
    defined class A 

    scala> class B extends Parent{ 
     | def name = "Bernardo" 
     | } 
    defined class B 

    scala> def addFamilyName[T <: Parent](fn:String, c:T{def name():String}) = c.name + " " + fn 
    addFamilyName: [T <: Parent](fn: String, c: T{def name(): String})java.lang.String 

    scala> addFamilyName("Martins", new A()) 
    <console>:11: error: type mismatch; 
    found : A 
    required: ?{def name(): String} 
      addFamilyName("Martins", new A()) 
          ^

だから、基本的に、私は、特定のタイプのサブクラスでもあり、また署名def name():String有する方法を含むパラメータタイプを定義したいです。

注:私のクラス階層はすでに複雑になっているので、私はこの方法でやろうとしています。このことを踏まえて、避けることができる場合は、ParentWithNameabstract classまたはtraitを追加しない方がよいです。

+2

メソッド 'name'と' name() 'は同じものではありません。後者を呼び出すことは前者の構文で行うことができますが、それは明確で構造的な型であり、特にそれらを同じではないと考えています。 –

答えて

6

それを信じているかどうかは、問題がメソッドシグネチャのカッコ内にあることです。これは動作します:

def addFamilyName[T <: Parent](fn:String, c:T{def name:String}) = 
    c.name + " " + fn 

実際にタイプパラメータを追加する必要はありませんが、追加する必要があります。これはまあまあです:

def addFamilyName(fn:String, c:Parent{def name:String}) = 
    c.name + " " + fn 
+0

うわー。それは...予期せぬことだった!あなたは何かを理解して読めるようになっていますか? いずれにしても、次にこのような問題が発生した場合は、括弧を追加して削除するようにします。ありがとう。 :) –

+0

@Alexandreなぜか分かりません。私は関数を返すメソッドの場合、あいまいさを防ぐことだと思うが、わからない。 – Owen

+0

インタプリタを少し掘り下げて、それを説明しました(私は答えに追加しました)。もう一度Owenに助けてくれてありがとう! –

関連する問題