English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية

Java 基礎教程

Java 流程控制

Java 数组

Java 面向对象(I)

Java 面向对象(II)

Java 面向对象(III)

Java 異常処理

Java 列表(List)

Java Queue(队列)

Java Map集合

Java Set集合

Java 输入输出(I/O)

Java Reader/Writer

Javaの他のトピック

Java インターフェース(Interface)

このチュートリアルでは、Javaのインターフェースを学びます。例を用いてインターフェースの実装方法や使用時期を学びます。

Javaでは、インターフェースは他のクラスが実装する必要がある一連の規範を定義します。例えば、

interface Polygon {
   public void getArea();
}

ここではPolygonがインターフェースです。interfaceキーワードを使用してインターフェースを宣言しています。

getArea()メソッドは、Polygonインターフェースで定義された規範であり、このインターフェースを使用するすべてのクラスはgetArea()メソッドを実装する必要があります。

インターフェースには抽象メソッドや定数を含むことができます。例えば、

interface Polygon {
   public static final String color = "blue";
   
   public  void getArea();
}

上記の例では、インターフェースPolygonを作成しました。それには、定数変数colorと抽象メソッドgetArea()が含まれています。

重要なのは、インターフェース内のすべてのメソッドが暗黙的にpublicであり、すべてのフィールドが暗黙的にpublic static finalであることに注意してください。したがって、インターフェース内でアクセス修飾子を指定する必要はありません。例えば、上記のコードを以下のように書けることができます

interface Polygon {
   String color = "blue";
   
    void getArea();
}

インターフェースとimplementsキーワード

抽象クラスと同様に、インターフェースのオブジェクトを作成することはできません。しかし、他のクラスでインターフェースを実装できます。Javaでは、implementsキーワードを使用してインターフェースを実装します。例えば、

interface Polygon {
    void getArea(int length, int breadth);
}
class Rectangle implements Polygon {
    public void getArea(int length, int breadth) {
        System.out.println("矩形の面積は " + (length * breadth));
    }
}
class Main {
    public static void main(String[] args) {
        Rectangle r1 = new Rectangle();
        r1.getArea(5, 6);
    }
}

出力結果

矩形の面積は 30

上記のプログラムでは、インターフェースPolygonを作成しました。Polygonインターフェースには抽象メソッドgetArea()があります。

 これは、Polygonを実装するどんなクラスでもgetArea()メソッドの実装を提供する必要があることを意味します。

注意を払ってください、Rectangleクラス(Polygonインターフェースを実装する)には、実装されたメソッドgetArea()があります。

なぜインターフェースを使用するのでしょうか?

インターフェースが何かを知った今、Javaでインターフェースを使用する理由について説明しましょう。

  • インターフェースはクラス(それを実装する)が従う規範を提供します。

  • 上記の例では、getArea()をインターフェースPolygonの規範として使用しました。これにより、各多边形の面積を取得できるというルールが設定されています。したがって、Polygonインターフェースを実装するどんなクラスでもgetArea()メソッドの実装を提供する必要があります。

  • 抽象クラスと同様に、インターフェースはJavaの抽象を実現するのに役立ちます。ここでは、getArea()は多边形の面積を計算するとして知られていますが、異なる多边形で面積を計算する方法は異なります。したがって、getArea()の実装は独立です。

  • インターフェースはJavaで多重継承を実現するために使用されます。もし子クラスが2つ以上のクラスから継承されている場合、それは多重継承です。

    Javaでは、クラスを継承することで多重継承を実現することはできません。しかし、クラスは複数のインターフェースを実装できます。これにより、Javaでの多重継承の機能を得ることができます。例えば、

    インターフェース Line {
       ...
    }
    interface Polygon {
       ...
    }
    class Rectangle implements Line, Polygon{
       ...
    }

    ここでは、RectangleはLineとPolygonのすべてのメソッドの実装を提供する必要があります。

インターフェース内のプライベートメソッドと静的メソッド

Java 8では、インターフェースは現在静的メソッドを含むことができます。

クラスと同様に、そのリファレンスを使用してインターフェースの静的メソッドにアクセスできます。例えば、

Polygon.staticMethod();

また、インターフェースはJavaで 9リリース版ではプライベートメソッドがサポートされています。現在、インターフェースで使用することができますプライベートメソッドプライベート静的メソッド

インターフェースをインスタンス化することができないため、プライベートメソッドを補助メソッドとして使用し、インターフェース内の他のメソッドをサポートします。

インターフェースのデフォルトメソッド

Java 8中で、インターフェース内に実装されたメソッド(デフォルトメソッド)が導入されました。それ以前は、すべてのメソッドはJavaの抽象メソッドでした。

インターフェース内でデフォルトメソッドを宣言するには、defaultキーワードを使用します。例えば、

public default void getSides() {
   //getSides()の本体
}

デフォルトメソッドを使用する理由は何ですか?

Javaにデフォルトメソッドが導入された理由を理解するために、あるシチュエーションを例示しましょう。

インターフェースに新しいメソッドを追加する必要がある場合を想像しましょう。

このメソッドを簡単にインターフェースに追加できますが、これはまだ話の終わりではありません。このインターフェースを実装するすべてのクラスは、このメソッドの実装を提供する必要があります。

多くのクラスがこのインターフェースを実装している場合、すべてのクラスを追跡して変更する必要があります。これは煩雑で、エラーが発生しやすいです。

この問題を解決するために、Javaはデフォルトメソッドを導入しました。デフォルトメソッドは通常のメソッドのように継承されます。

デフォルトメソッドをよりよく理解するために、例を示しましょう。

例2:デフォルトメソッド

interface  Polygon {
   void getArea();
   default void getSides() {
      System.out.println("私は多角形の辺を取得できます。");
   }
}
class Rectangle implements Polygon {
   public void getArea() {
      int length = 6;
      int breadth = 5;
      int area = length * breadth;
      System.out.println("矩形の面積は "+area);
   }
   public void getSides() {
      System.out.println("私は四つの辺があります。");
   }
}
class Square implements Polygon {
   public void getArea() {
      int length = 5;
      int area = length * length;
      System.out.println("正方形の面積は "+area);
   }
}
class Main {
   public static void main(String[] args) {
      Rectangle r1 = new Rectangle();
      r1.getArea();
      r1.getSides();
      Square s1 = new Square();
      s1.getArea();
   }
}

出力結果

矩形の面積は 30
私は四つの辺があります。
正方形の面積は 25

上記の例では、我们はPolygonインターフェースを生成しました。PolygonにはデフォルトメソッドgetSides()と抽象メソッドgetArea()があります。

そして、RectangleクラスはPolygonを実装し、Rectangleは抽象メソッドgetArea()の実装を提供し、デフォルトメソッドgetSides()をオーバーライドします。

別のSquareクラスも作成しました。ここでは、Squareは抽象メソッドgetArea()の実装のみを提供しています。

インターフェースの実際のアプリケーション例

より実用的なJavaインターフェースの例を見てみましょう。

//sqrt関数を使用します
import java.lang.Math;
interface  Polygon {
   void getArea();
  
     //多角形の周長を計算します
   default void getPerimeter(int... sides) {
      int perimeter = 0;
      for (int side: sides) {
         perimeter += side;
      }
   System.out.println("周長: " + perimeter);
   }
}
class Triangle implements Polygon {
   private int a, b, c;
   private double s, area;
    //三角形的辺を初期化します
   Triangle(int a, int b, int c) {
      this.a = a;
      this.b = b;
      this.c = c;
      s = 0;
   }
    //三角形的面積を計算します
   public void getArea() {
      s = (double) (a + b + c)/2;
      area = Math.sqrt(s*(s-a)*(s-b)*(s-c));
      System.out.println("面積: " + area);
   }
}
class Main {
   public static void main(String[] args) {
      Triangle t1 = new Triangle(2, 3, 4);
      //Triangleクラスのメソッドを呼び出します
      t1.getArea();
      //Polygonクラスのメソッドを呼び出します
      t1.getPerimeter(2, 3, 4);
   }
}

出力結果

面積: 2.9047375096555625
周長: 9

上記のプログラムでは、インターフェースPolygonを作成しました。それはデフォルトメソッドgetParameter()と抽象メソッドgetArea()を含んでいます。

すべての多角形の周長を同じ方法で計算できます。したがって、PolygonクラスではgetPerimeter()のメイン部分を実装しました。そのため、Polygonを実装したすべての多角形はgetPerimeter()を使用して周長を計算できます。

しかし、面積の計算方法は、異なる多角形によって異なります。なぜなら、異なる多角形の面積計算のルールが異なるからです。

したがって、Polygon には実装されていないが getArea() が含まれています。また、Polygon インターフェースを実装するすべてのクラスは getArea() の実装を提供する必要があります。

インターフェースと extends キーワード

クラスと同様に、インターフェースも他のインターフェースを継承することができます。継承には extends キーワードを使用します。例えば、

インターフェース Line {
   //Line インターフェースのメンバー
}
インターフェース Polygon が Line を拡張します。
   //Polygon インターフェースと Line インターフェースのメンバー
}

上記の例では、インターフェース Polygon が Line インターフェースを拡張しています。したがって、Polygon を実装するクラスは、Line と Polygon のすべての抽象メソッドの実装を提供する必要があります。

注意、インターフェースは複数のインターフェースを継承することができます。これは、複数のインターフェースを実装するクラスに似ています。例えば、

インターフェース A {
   ...
}
インターフェース B {
   ... 
}
インターフェース C が A, B を拡張します。
   ...
}