2012-05-09 21 views
3

抽象クラスを確立しようとしています。私は、どのサブクラスにも潜在的なアクションを列挙するenumがあることを保証したいと思います。抽象クラスと列挙体

たとえば、Fooは抽象クラスです。

Fee extends Foo and can... 
    TALK 
    WALK 
    SLEEP 

Bar extends Foo and can... 
    SIT 
    STARE 

私は、親クラスにフィールドを与え、その子クラスに可能なアクションを列挙させたいと思います。どのように私はこれにアプローチするのですか?

たとえば、クラスに列挙型を定義すると、いくつかの一般的なアクションを与え、サブクラスに渡してサブクラスで列挙型を拡張できますか?それは別の選択肢かもしれない。

答えて

4

私はアプローチに同意することを知りませんが、あなたは

enum CanDos { 
    TALK, 
    WALK, 
    SLEEP, 
    SIT, 
    STARE 
} 

を行うことができますし、クラスが

abstract class Foo { 
    abstract Set<CanDos> getCanDos(); 
    //or 
    abstract boolean can(CanDos item); 
} 

を持っている可能性があり、あなたが効率的なストレージのためのEnumSetを使用することができます能力。

あなたが探しているのは、(あなたが言及している親抽象クラスのフィールドのような)列挙型のセットを提供するために必要なものなら、私はEnumSet<CanDos>があなたの男だと思います。その場合には

abstract class Foo { 

    private final Set<CanDos> candos; 

    protected Foo(Set<CanDos> candos) 
    { 
    this.candos = new EnumSet<CanDos>(candos); 
    } 

    public boolean can(CanDos item) { 
    return candos.contains(item); 
    } 
} 

代わりに、あなたは完全に抽象クラスを避けることができ(あるいは少なくともそれは、例えばthis questionまたはthis one参照強制ではありません)。よく考えられている本有効なJavaは "Prefer interfaces to abstract classes"を提案します。あなたが本当に(あなたがハードについて考えなければならない)一般的な継承のルートに値があると思う場合は

enum CanDos { 
    TALK, 
    WALK, 
    SLEEP, 
    SIT, 
    STARE 
} 

public interface FooThatCanDo { 
    boolean can(CanDos item); 
} 

代わりにこれを行うには、上記のように、あなたは抽象的な基本実装を提供できる、とすることを宣言しますそれはimplements FooThatCanDoです。

+0

私は、これらのことのそれぞれを行う標準的な方法(つまり、最終的なメソッドdoStuff(CanDo doThis))があるので、抽象クラスが欲しいと思います。これは良いアイデアのように聞こえる? – gobernador

+0

@gobernador:私は最初にガイダンスを見に行くだろう。抽象クラスを使用する理由は十分ありますが、できるだけ避けるべき理由があります。私はトピックhttp://my.safaribooksonline.com/book/programming/java/9780137150021/classes-and-interfaces/ch04lev1sec6または少なくともこの質問で効果的なJavaのセクションを読むことをお勧めします:http://stackoverflow.com/questions/56867/interface-vs-base-classを入力し、条件があなたに適用されるかどうか尋ねます。 – andersoj

+0

@gobernador:抽象クラスを作成し、それを継承するのではなく、サブクラスのフィールドとしてコンポジションに含める/サブクラス化することもできます。これは、不都合な継承ツリーを接合しないで共通のコードを持つことができる良い中間地になる可能性があります。あなたが上記のあなたの特定の問題についてもっと詳しく書くなら、もっと多くを提供できるかもしれません。 – andersoj

0

私はあなたが探しているものではないと思いますが、少なくとも直接はありません。おそらくBitSetを使用することができます。

class Base { 
    private static EnumSet actions; 

    public EnumSet getActions() { return actions; } 
} 

class Derived extends Base { 
    private static EnumSet actions; 

    @Override 
    public EnumSet getActions() { 
     return new EnumSet(actions).addAll(super.getActions()); 
    } 
}