Upload
appresso-engineering-team
View
328
Download
1
Embed Size (px)
Citation preview
Effective Java 輪読会Item 43-44
開発部 陳映融 2014/2/12
第 7 章 メソッド
項目 38 パラメータの正当性を検査する 項目 39 必要な場合には、防御的にコピーする 項目 40 メソッドのシグニチャを注意深く設計する 項目 41 オーバーロードを注意して使用する 項目 42 可変長引数を注意して使用する
項目 43 null ではなく、空配列か空コレクションを返す 項目 44 すべての公開 API 要素に対してドキュメントコメントを
書く
2
Item 43null ではなく、空配列か空コレクションを返す
目当ての物がないときは何を返す?
4
店でチーズを買おうとしたら、チーズがない状況
チーズがないという特別な状況のため、余分な処理が必要となる
private final List<Cheese> cheesesInStock = ...;
/** * @return 店にあるすべてのチーズを含む配列、もしくは、 * 買えるチーズがなければ null 。 */public Cheese[] getCheeses() { if (cheesesInStock.size() == 0) // なぜかチーズがない状況を特別扱いにする return null; ...}
Cheese[] cheeses = shop.getCheeses();if (cheeses != null && // 戻り値を使う前に余分な null チェックが必要 Arrays.asList(cheeses).contains(Cheese.STILTON)) System.out.println("Jolly good, just the thing.");
なぜ null を返す?
5
主張:『配列を割り当てるコストを回避できるので、空配列よりも好ましい』
反論1:そのメソッドがパフォーマンス上の本当の原因?プロファイリングでそう示された?でなければ、そのレベルで心配することではない それって、時期尚早の最適化かもしれない 項目 55 「注意して最適化する」を参照
反論2:項目を一つも返さない呼び出しすべてが、同一の長さゼロの配列を返すことが可能。割り当てるコストはかからない 長さゼロ配列は不変 不変オブジェクトは制限なく共有しても問題ない 項目 15 「可変性を最小限にする」を参照
コレクションから配列を返す方法
6
コレクションから指定した型の配列を書き出すための標準イデオム// コレクションから配列を返す正しい方法
private final List<Cheese> cheesesInStock = ...;private static final Cheese[] EMPTY_CHEESE_ARRAY = new Cheese[0];
/** * @return 店にあるすべてのチーズを含む配列。 */public Cheese[] getCheeses() { // Collections.toArray(T[]) の仕様は、 // 入力配列がコレクションを保持するのに十分な大きさであれば、入力配列を返すことを保証する // したがって、空配列を割り当てることはない return cheesesInStock.toArray(EMPTY_CHEESE_ARRAY); }
コレクションを返すメソッドの場合
7
同一の不変の空コレクションを返すことはできる
ちなみに Collections.emptyList や emptySet 、 emptyMap があるが Arrays.emptyArray はない(項目 25 参照)
// コレクションのコピーを返す正しい方法public List<Cheese> getCheeses() { if (cheesesInStock.isEmpty()) return Collections.emptyList(); return new ArrayList<>(cheesesInStock);}
まとめ
8
配列やコレクションを返すメソッドが、空配列や空コレクションの代わりに、 null を返すべき理由は決してない
配列を返すメソッドの戻り値として空配列を返す場合、同一の長さゼロ配列を返す
コレクションを返すメソッドの戻り値として不変の空コレクションを返す場合は、 Collections.emptyXXX メソッドを使用する
Item 44すべての公開 API 要素に対して
ドキュメントコメントを書く
API のドキュメント
10
Javadoc ドキュメンテーションコメント、またはドキュメントコメントと呼ばれ
たもの ソースコードから自動的に API ドキュメント( HTML )を生成する 規約 : “How to Write Doc Comments for the Javadoc Tool”
ドキュメントコメントの記述対象 すべての公開されている物※の宣言の前にドキュメントコメントを書く 保守可能なコードを書くためには、ほとんどの公開されていない物※に対
しても書くべき ドキュメントコメントの保守コストを考慮すればコードの可読性を上げる方向
もある
※ クラス、インタフェース、コンストラクタ、メソッド、フィールド
ドキュメントコメントの記述原則
11
対象要素共通 最初の一文に概要説明を記述する
クラス シリアライズ可能であれば、シリアライズ形式を文書化すべき スレッド安全性について記述すべき(項目 70 ) ジェネリック型の型パラメータを文書化すべき enum 型は public メソッドだけでなく、定数も文書化する
アノテーション すべてのメンバーを文書化する
ドキュメントコメントの記述原則
12
メソッド メソッドのクライアントとの間の契約を簡潔に記述すべき
何を行っているかを述べる。どのように処理を行っているかではない ただし、継承のために設計されたクラスでのメソッドは例外(項目 17 )
@param タグ : すべてのパラメータに対して記述 @return タグ : 戻り値があれば @throws タグ : スローするすべての例外に対して記述 (項目 62 )
すべての事前条件と事後条件を列挙すべき メソッドの副作用も文書化すべき ジェネリックメソッドの型パラメータを文書化すべき
ドキュメントコメントの記述原則
13
コード例を記述する場合は Javadoc の {@code} タグが好ましい {@code} タグ内の HTML メタ文字はそのまま使用できる HTML の <code> や <tt> タグだと、メタ文字をエスケープする必要
がある
単語 “ this” の使用について 慣習的、呼び出されたインスタンスメソッドのオブジェクトのことを指
す
HTML メタ文字( <, >, & )の生成は {@literal} タグが良い 変換後のドキュメントだけ考えるなら “ <” “>” “&” で
もいいが ソースコードと生成結果の両方の読みやすさを意識すべき
実務においてのドキュメントコメント
14
概要説明の記述慣例 メソッドやコンストラクタ : 処理を説明する動詞句 クラス、インターフェイス、フィールド :表される事柄を説明する名詞句
パッケージレベルのドキュメントコメント Java 1.5 以降は package-info.java に書くべき パッケージ宣言とパッケージアノテーションを入れることできる(必須で
はない)
メソッドコメントは {@inheritDoc} タグで内容を一部継承できる スーパークラスよりインターフェイスが優先される 継承することで文書を再利用可能(独自の制約があって、使いにくいけ
ど ... )
必要があれば、外部文書へのリンクを含む
ドキュメントコメントの継承例
15
サンプルのクラス図
Javadoc 生成結果file:///item44_javadoc/item44/package-tree.html
これらのクラスのメソッドに {@inheritDoc} を記述
まとめ
16
すべての公開 API 要素に対してドキュメントコメントを記述
ドキュメントコメント内で標準規約に従った統一されたスタイルを採用
ドキュメントコメント内の HTML メタ文字は取扱い要注意