■static宣言■

Javaの最初から使用していたmain関数を含むクラスには,staticキーワードが使用されていた.ようやく,その意味を解説する準備が整った.

staticとは

static修飾子は,メンバ変数あるいはメソッドの宣言に使用することができる.(クラス名の宣言の所には使用できない.)

public class Hello    //このクラス名の所にはstaticを追加できない.
{
  static int s; //クラス変数
  int i; //インスタンス変数

  public static void main(String[] args) //クラスメソッド
  {
     System.out.println(s);  //○クラス変数を使用できる
     System.out.println(i);  //×エラーになる
  }

  public void funcA() //インスタンスメソッド
  {
     System.out.println(s);  //○クラス変数も使用できる
     System.out.println(i);  //○インスタンス変数も使用できる
  }
}

static宣言されたメンバ変数とメソッドのことをそれぞれクラス変数とクラスメソッドと呼ぶ.対して,宣言されていない普通のメンバ変数とメソッドのことをインスタンス変数とインスタンスメソッドと呼び,両者を区別する.

両者の違いは,動作時の所属先が異なる点である.クラス変数とクラスメソッドは,クラスに所属する.対してインスタンス変数とインスタンスメソッドは,個々のインスタンス(オブジェクト)に所属する.

クラス変数とインスタンス変数

まずメンバ変数について説明する.インスタンス変数は,オブジェクトに所属するため,同じクラスから生成されたオブジェクトでも,別オブジェクトのクラス変数は,あくまで別の変数として扱われる.しかし,クラス変数はオブジェクトとは関係なく,そのクラスを参照できる部分ならば,どこからでも共通の変数として共有される.

例えば,次の2つのオブジェクトを生成する.

Hello h1 = new Hello();
Hello h2 = new Hello();

同じHelloクラスから生成されたオブジェクトh1とh2だが,インスタンス変数h1.iとh2.iは,どちらも名前iだが,別の変数である.どちらかが書き換わっても,互いに影響しない.

しかし,クラス変数h1.sとh2.sは,実は同じ変数を意味する.どちらかが書き換わるともう一方も書き換わる.

クラスメソッドとインスタンスメソッド

メソッドとは,つまりプログラムコードである.オブジェクト別にわざわざプログラムコードまで複製する必要がないため,クラスメソッドもインスタンスメソッドも結局同じものが動作する.しかし,メソッドに対してクラス変数・インスタンス変数との間の関係を明確にするため,クラスメソッドとインスタンスメソッドが区別される.

最初の例に示したように,static宣言されたクラスメソッドでは,同じくstatic宣言されたクラス変数だけを参照することができ,インスタンス変数を参照しようとするとエラーとなる制限が付けられている.次に説明するように,クラスに固有なクラスメソッドは,オブジェクトを生成しないまま利用されることもあるため,オブジェクト別に存在する変数を利用しようとしてもできない可能性があるためである.

クラス変数とクラスメソッドの参照方法

クラス変数やクラスメソッドへのアクセス方法は,先ほどの例ではh1.sやh2.sのようにオブジェクト名.変数名やオブジェクト名.メソッド名でも参照できるものの,インスタンス変数やインスタンスメソッドと混乱してしまう.そこで,次のように,クラス名.クラス変数名またはクラス名.クラスメソッド名としてアクセスすることが望ましい.

Hello.s
Hello.funcA

演習課題7

次のような画像処理を行うstaticメソッドを集めた画像処理クラスIPLを作成せよ.

public class IPL
{
  staticなメソッド1
  staticなメソッド2
  ...
}

作成するメソッドは次のもの.

void copyImage(入力画像,出力画像); //入力画像から画像の内容をそのまま出力画像にコピー
void mirrorImage(入力画像,出力画像); //左右反転
void mirrorImageV(入力画像,出力画像); //上下反転

このようなIPLクラスを使って,し,実際にmainから動作させてみよ.