Back To Main


┏━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
┃ ◆Javaで珈琲ブレイク vol.009 前編◆
┃……………………………………………………………………………………………
┃ [不定期] まぐまぐ ID=0000088576 Melma! ID=m00061296
┃……………………………………………………………………………………………
┃ 今回からご覧になる方は、バックナンバーご活用下さい
┃ http://www.melma.com/mag/96/m00061296/
┃ http://backno.mag2.com/reader/Back?id=0000088576
┗━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

◆目次◆

■Java documentation超入門
■@param、@return、@exceptionタグは絶対必須
■@authorタグ
■@version、@sinceタグ


皆さん、こんにちは。

Mr.Hackです。五月も終わってしまいましたね。最近C#を勉強し始めたのですが、思っていた以上にJavaと似てますね。基本的にはC++の方にシンタックス等は近いのですが、Javaの良い要素を取り入れた感じです。まだ勉強したてですが、思ったことは、

Javaをしっかり勉強していれば、C#はとりわけ問題なし

です。キーワード・クラス名になれるまでは、少々勉強が必要ですが、あとは、OOPの醍醐味である継承(inheritance)、多形性(polymorphism、ギリシャ語でmany formsの意味)、データのカプセル化(隠蔽化、encapsulation)の概念はJavaでなれていれば問題なしです。皆さんの中には、マイクロソフトが提唱したDot Net Frameworkに興味があり、C#も勉強してみたい!という方もいらっしゃるでしょう。でも、もう少し他の言語に浮気をせずにがんばってみて下さいね。Javaをしっかりマスターすれば、C#はもちろん、C++等をつかってOOPが出来るようになります。

さて、前回の続きからいってみましょう。前回は、一般的なExceptionを使うのはよろしくないことを勉強しました。今週は、前回残しておいたJava documentationを勉強しましょう。

■Java documentation超入門
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
Javaドキュメントとは、クラスの仕様を記述したHTML形式のファイルです。もう皆さんは幾度となくJava SDK API仕様書でお目にかかっていますね。BankAccountのAPI仕様もダウンロードしてご覧になったと思います。javadocコマンドでクラスのドキュメント(API仕様書)を作成します。

なぜ、皆さんはJavaドキュメントを作成しなければならいのですか?

そう、『読みやすさ』(Readability)の向上のためですね。これは、ソフトウェアの保守(maintenance)にも貢献します。vol.001でもふれましたが、1ヶ月前に3000行も書いたプログラムがどんな機能を持っていたのか思い出せますか?1年前のはどうですか?もし、他人があなたの書いたプログラムを見たら瞬時にそのクラス・メソッドの意図・目的を把握出来ますか?ある意味、Javaドキュメントは、あなたが書いたクラスの使い方を示したメモ書きということが出来ます。使い方を示すわけですから、使い方が分かるように記述しないといけませんね。

では、早速Javaドキュメントを作成してみましょう。前回のvol.008使ったファイル、BankAccount.javaとBankAccountTest.javaのドキュメントをCPadで開いて下さい。開きましたら、右側上側の青い三角アイコンの実行をクリックしてください。クリックすると、コマンドプロンプトが開きます。そこで、
┌──────────────────────────────────┐
dir
└──────────────────────────────────┘

とタイプして現在のフォルダ(ディレクトリ)にBankAccount.javaとBankAccount.javaファイルがあることを確認して下さい(ない方は、そのファイルをおいてある場所までcdコマンドで移動して下さい)。確認しましたら、

┌──────────────────────────────────┐
javadoc BankAccount.java
└──────────────────────────────────┘

とタイプして下さい。そうすると、

┌──────────────────────────────────┐

ソースファイル BankAccount.java を読み込んでいます...
Javadoc 情報を構築しています...
全パッケージとクラスの階層ツリーを作成しています...
全パッケージとクラスのインデックスを作成しています...
overview-tree.html の生成
index-all.html の生成
deprecated-list.html の生成
全クラスのインデックスを作成しています...
allclasses-frame.html の生成
index.html の生成
packages.html の生成
BankAccount.html の生成
serialized-form.html の生成
package-list の生成
help-doc.html の生成
stylesheet.css の生成

└──────────────────────────────────┘

とメッセージが表示され、拡張子がhtmlのファイルがずらりと作成されます。CPadにもどり、メニューから『実行』→『エクスプローラーを起動』を選択して、エクスプローラーを起動します。起動するとhtmlが生成されたフォルダが開くので、そのなかから、index.htmlファイルを選択しダブルクリック(または、クリック)します。どうですか?クラス BankAccountが表示されましたか?作成は何とも簡単でしたね。javadocコマンドにJavaドキュメントを作成したいファイルネーム(javaの拡張子までふくめる)をタイプするだけで作成出来ました。

複数のクラスのドキュメントを作成するときはどうすればいいのでしょうか?

作成したいjavaファイルを半角スペースで区切って並べます。または、javadocコマンドの後に続くクラス名指定のところで、アスタリスクマーク(*)を使います。そのフォルダにある拡張子がjavaである全てのファイルに対してドキュメントが作成されます。

┌──────────────────────────────────┐
 javadoc BankAccount.java BankAccountTest.java
 または、
javadoc *.java
└──────────────────────────────────┘


では、実際にBankAccountクラスのドキュメントがBankAccount.javaの/** */を使ったコメントにどのように対応しているか見てみましょう。

BankAccountクラスのドキュメントとBankAccount.javaを見比べて見るとおわかりになると思いますが、/** */でくくられたコメントしか、実際にドキュメントとして現れていないことに気づきましたか?それも、コンストラクタ・メソッド内に記述した/** */も現れません。試しに、BankAccountのコンストラクタを下記のようにコメントしてもう一度javadocコマンドを先ほどのように実行して下さい。

┌──────────────────────────────────┐

/**
* 残高をゼロにセットするデフォルトコンストラクタ。初期化時、
* 残高をゼロにセットする。
*
* @author Mr.Hack
* @since 1.0.0
*/

/*
* このコメントもJavaドキュメントに現れない。
*/
public BankAccount() {
// これは、Javaドキュメントに現れない。
/* もちろんこれも。*/
/**
* コンストラクタ・メソッドの中では、ドキュメンテーション・
* コメントを使っても現れない
*/
this.balance = 0;
}

└──────────────────────────────────┘

つまり、Javaドキュメントはフィールドとメソッドとそれを含むクラスを説明するもので、メソッド内のロジックやローカル変数は、基本的にドキュメントの対象にならないということを頭に入れておいて下さい。このクラスを使うプログラマ(ユーザー)はクラスがどのような働きをするか、ということはとても関心事です。public(ここでは、publicがつくとクラス外の誰でもアクセス可能と覚えておきましょう)なフィールドとpublicなメソッドも関心事です。というのは、そのフィールドとメソッドはプログラマが使用する(使用できる)からです。しかしながら、あるメソッドの中身はどうでもいいのです。withdraw()メソッドのなかですごーい計算をしていようが、たった一行のコードであろうが関心事ではないのです。関心事は、withdraw()メソッドを使ったときにちゃんとしたアウトプットさえ出してくれればいいのです。vol.000でニワトリの例を覚えていますか?餌を与えて、ちゃんと卵を出してくれるということがニワトリを使用する(飼う)人には重要なのです。太っていようが痩せていようが、餌を与えて卵さえ出してくれれば問題ありません。したがってメソッド内のロジックやローカル変数のコメントは使う側のプログラマ(ユーザー)には必要ないのです。

publicキーワードがでたついでに、privateキーワードをざっとふれておきましょう。BankAccount.javaのインスタンス変数balanceのように、publicの代わりにprivateを使用するとそのbalanceはクラス外からは誰もアクセスすることが出来ません。つまり、BankAccountクラスのユーザーであるプログラマやクライアントである他のクラスはそのbalance変数にアクセスすることが出来ません。アクセスするとは、balanceに新しい値を代入したり、balanceから直接値を取り出すということです。それゆえ、privateキーワードがついたフィールド、メソッドは、同じくユーザーであるプログラマには関心事ではないのです。アクセス出来ないのですから。そのため、デフォルトでは、privateのコメントは/** */を使っても現れません。

次は、BankAccountクラスのAPI仕様のコンストラクタの概要とメソッドの概要を見て下さい。簡潔に一文で説明が述べられていますね。『一文』というのがみそです。/**で始まるコメントで、最初のマルで終わる『一文』が概要として記述されます。英語ですと、ピリオドですね。つまり、一文で簡潔かつそのコンストラクタ・メソッドを端的に表す説明文を記述しなければなりません。それ以降の文はどうなるかといいますと、各概要のリンクをクリックした、詳細に現れます。

上記のBankAccountクラスのコンストラクタの例でいいますと、最初の一文

┌──────────────────────────────────┐
残高をゼロにセットするデフォルトコンストラクタ。
└──────────────────────────────────┘

だけが、コンストラクタの概要に現れ、それに続く文、

┌──────────────────────────────────┐
初期化時、残高をゼロにセットする。
└──────────────────────────────────┘

は概要にあるリンクをクリックした先のコンストラクタの詳細に、最初の一文につづいて現れます。

■@param、@return、@exceptionは絶対必須
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
コンストラクタ・メソッドのコメントで重要な記述は何でしょう?

@paramタグ

値・参照が渡される型とパラメータの数は重要ですね。それを使うクライアントが間違った型と数を使用するとコンパイルエラーになってしまいますから。そのため、パラメータがある場合は、必ず、

┌──────────────────────────────────┐

@param パラメータ変数名 それの記述

例: @param amount 入金する金額

└──────────────────────────────────┘

というように記述します。

@returnタグ

メソッドに戻り値がある場合、どんな値が返されるのかということはそのメソッドを使うプログラマには大変な関心事です。たとえば、戻り値の型がdouble型と分かっていてもそれが、残高を表すのか、それ以外の特別な数値を表すのか、分かりません。実際は、メソッドの名前から推測は付きますが、100%推測出来るとはかぎりませんね。ですから、この記述は非常に重要です。戻り値がある場合は、

┌──────────────────────────────────┐

@return 変数名 それの記述

例: @return amount 入金する金額

└──────────────────────────────────┘

と記述します。戻り値が一つの変数名でない場合は(たとえば、そのメソッドが他のメソッドを呼び出し、そのまま呼び出した値をそのまま返却するようなときは、変数名を記述しないで、その変数名の記述だけ記述します。例えば、

┌──────────────────────────────────┐

/**
* ドル建てで引き出す。
*
* @return USドル
*/
public double withdrawWithDollar() {
 //convertToDollar()は円をドルに変換してドルを戻り値として返す。
return convertToDollar(yen);
}

└──────────────────────────────────┘

のようにします。

@exceptionタグ (または、@throwsタグ)

コンストラクタ・メソッドが、ある例外をスローする場合は、その例外を必ず記述します。記述方法は、

┌──────────────────────────────────┐

@exception クラス名 どんな場合に例外が発生するかを記述

└──────────────────────────────────┘

というようにします。複数個スローする場合はそれぞれの例外に@exceptionタグを使います。例えば、

┌──────────────────────────────────┐

/**
* バッファーに蓄えられた文字列をdouble型に変換して返す。
*
* @return double型の数値
* @exception IOException IOエラーが発生した場合
* @exception NumberFormatException バッファーに蓄えられた文字列が
*                  数字ではない場合
*/
public double readDouble() throws IOException, NumberFormatException {
return Double.parseDouble(buffer.readLine());
}

└──────────────────────────────────┘

のようにします。例外はランタイム(RuntimeExceptionかそのサブクラス)でも必ず記入するようにして下さい。とりわけ、ランタイムの例外はコンパイル時にエラーとならないので、使う側のプログラマも油断しがちです。@exceptionタグがなければ、プログラマは例外が発生しないものと思います。これは、とても危険ですね。か・な・ら・ず・記入して下さいね。

今述べた3項目は全てのコンストラクタ・メソッドでチェックして当てはまるものがあれば、必ず記入するようにしましょう。

そのほかにもまだまだ、便利なタグがあります。

■@authorタグ
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

これは、いわゆるクラスの著者を記述します。記述方法は、
┌──────────────────────────────────┐

@author 著者の名前

例:@author Mr.Hack

└──────────────────────────────────┘

とします。このタグはデフォルトではHTMLに反映されません。基本的には誰が書いたかという情報は、ドキュメントとしては、余分な情報であると考えられるからです。というのも、本来のJavaドキュメントの役割は、ソースコードがあればその読みやすさ、そのコードがどのような機能を果たしているかを、そのソースコードを書いた著者を抜きに、読みとれるような内容を、ユーザーであるプログラマに提供することです。つまり、著者と連絡をわざわざ取らなくてもドキュメントから使い方を学び、使用できるようにするのがドキュメントの役割なのです。とはいっても、プロジェクトチームベースでのAPIの開発という観点からすれば、このクラスは誰が書いたかという責任の所在がはっきりしていた方がそのクラスを発展させる時には、やりやすいでしょうね。ですから、
クラス・インターフェイスには必ず@authorタグを入れましょう。

複数人いる場合はどうしましょう?複数人いる場合は、それぞれに@authorタグをつかい、オリジナルの著者を一番上に、それ以外は、名前順(普通は苗字、last name)で記入します。

┌──────────────────────────────────┐

@author Mr.Hack
@author John Doe(co-author)
@author John Smith(modification)

└──────────────────────────────────┘

■@version、@sinceタグ
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
@version、@sinceにはバージョン情報を記入します。記入方法は、

┌──────────────────────────────────┐

@version バージョンナンバー
@since バージョンナンバー

例:
@version 1.0.1
@since 1.0.0

└──────────────────────────────────┘

API仕様にもバージョンがあります。例えば、Java SDK 1.3.2というのが、バージョンです。@sinceタグはそのクラスまた、クラスの中のメソッドがいつのバージョンで導入されたかを記述します。たとえばSDK APIのSystemクラスを見て下さい。それには、

導入されたバージョン:
JDK1.0

とあります。すなわち、1.0の時に導入されたということがこの@sinceタグから分かります。@sinceタグを使うと『導入されたバージョン:』という記述が自動的に挿入されます。このタグはクラスには必ず記入し、メソッド・フィールドには新しく導入された場合に限り、その導入されれた時のバージョンを@sinceタグを使って記入するようにします。

では、@versionタグは何を意味するのでしょう?これは、今現在の(最新の)versionを記述します。たとえば、SDKの1.3.2のバージョンですと@version 1.3.2ですね。しかしながら、@versionタグはデフォルトのjavadocではHTMLに反映されないようになっています。というのも、API仕様がディストリビュート(配布)されるときは、パッケージ(クラスの集まり)の場合が多いためだとおもいます。パッケージのトップには、普通API仕様のバージョンを記述しますので(SDK API仕様を見ると、トップのページに『JavaTM Platform, Standard Edition, v 1.3 API 仕様』とある)わざわざ一つ一つのクラスにそのバージョンを記載しなくても自明だからでしょう。一方で、クラスによってはバグをなおしたりしてメイジャーバージョンとマイナーバージョンが同じでもバグフィクスバージョンが違ったりする場合があります。そのため、API仕様として配布するバージョンは、1.3でもバグフィクスバージョンが1.3.1から1.3.2に変わるという場合もありますので、やはり、各クラスに@versionタグを必ず記入しましょう。

ところで、バージョンを表す、1.3.2とはどういう意味なのでしょう?

引き続き、後編をお楽しみ下さい。

━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
◆Javaで珈琲ブレイク◆
────────────────────────────────────
皆様からの激励・批判のメールをお待ちしております。
【発行者】 Mr.Hack - javacafebreak@hotmail.com
【掲示板】 http://fweb.midi.co.jp/~romanhikou/cafe_entrance.html
※質問は上記の掲示板からどうぞ。
【サイト】 http://mrhack.hoops.ne.jp/
【発行数】 まぐまぐ[885] Melma[134]
【解除】http://mrhack.hoops.ne.jp/
※解除は上記のサイトからいつでもできます。
────────────────────────────────────
(c)2002 MR.HACK ALL RIGHTS RESERVED
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━

© 2002 MR.HACK ALL RIGHTS RESERVED