検索
連載

定数をインターフェイスに移したら「あいまい」エラーJavaTips 〜Javaプログラミング編

Share
Tweet
LINE
Hatena

 インターフェイスはスーパークラスと異なり、メソッドの具象や変数の定義はできませんが、1つのクラスに複数の実装をすることができますし、定数の定義と初期化ができますので、プロジェクトやチームにおいて定数を共有する場合にも便利です。

 しかし、実装した複数のインターフェイスに同名の定数がある場合には注意が必要です。実装した時点では何も問題は起こりませんが、この定数を用いたところで「フィールド(変数名)はあいまいです」という分かりづらいコンパイルエラーが発生するからです。

 例えば、プロジェクト共通のインターフェイスを実装し、そのインターフェイスで定義されている定数と同じ名前の定数を定義している下図のクラスがあるとしましょう。

インターフェイスで定義されている定数と同じ名前の定数を定義しているクラス
インターフェイスで定義されている定数と同じ名前の定数を定義しているクラス

 ご覧のとおり、定数名「PI」のみで呼び出された場合、クラスで定義した方の定数PIが用いられ、インターフェイスにある同名の定数は用いられません。

 さて、ここで、下図のようにプロジェクト専用のインターフェイスを新たに作成し、実装に追加することにして、クラスで定義していた定数PIを移したところ、「フィールド PI はあいまいです」というエラーが出てしまいました。

2つのインターフェイスで定義している同じ名前の定数を使った場合のエラー
2つのインターフェイスで定義している同じ名前の定数を使った場合のエラー

 これは、インターフェイスを複数実装した場合に、その順番には特に意味はなく、平等に扱われることから起こります。この場合、定数名の前にインターフェイス名を付けて「ProjectR.PI」のように指定すると、コンパイルエラーは解消しますが、インターフェイスとして実装するメリットが半減してしまいます。

 もう1つの解決策として、この2つのインターフェイスの位置付けによっては、継承関係を持たせることも考えられます。そして、下図のようにサブインターフェイスのみを実装するようにすれば、サブインターフェイスで定義している定数が優先して用いられます。

インターフェイス間の継承を定義し、サブインターフェイスのみ実装すると解決
インターフェイス間の継承を定義し、サブインターフェイスのみ実装すると解決

 なお、ここでスーパーインターフェイスも実装してしまうと、同じエラーになってしまいます。ちなみに、スーパーインターフェイスとサブインターフェイスの両方を実装することそのものはコンパイルエラーにはなりません(意味がないことですが)。

Profile

RunDog.org

平野正喜


Copyright © ITmedia, Inc. All Rights Reserved.

ページトップに戻る