Javaのデータ型は「基本データ型」と「クラス型」の大きく2つのデータ型に判別されます。基本データ型とはintやdouble、boolean、charのようなクラスライブラリとは独立してデフォルトで使用することができるデータ型のことをいいます。
基本データ型に属する値を型変換したいという場合、また、クラス型として基本データ型を操作したいという場合には、いったん「基本データ型をクラス型として扱えるようにしてやる」必要があります(なぜなら、基本データ型はクラス型のようにメソッドを持たず、「+」や「*」のような演算子でしか操作すること ができないからです。当然、これらの演算子では型変 換などは行なうことができません)。このように、基本 データ型に「クラス型としての体裁を与える(ラッピン グする)」クラスを「ラッパクラス」といいます)。このように、基本データ型をクラス型として扱うためにラッピングするクラスをラッパクラスといいます。
ここでは、このラッパクラスとコンテキスト属性を利用して、簡易なアクセスカウンタを生成してみることにします。
<%@ page contentType="text/html;charset=Shift_JIS" %>
<%
Integer intCnt;
Object objCnt=application.getAttribute("counter");
if((Integer)objCnt==null){
intCnt=new Integer(1);
}else{
intCnt=(Integer)objCnt;
intCnt=new Integer(intCnt.intValue()+1);
}
application.setAttribute("counter",intCnt);
%>
あなたは<%=intCnt%>人目のお客さまです。
コンテキスト属性“counter”を取得し、すでに値が存在する場合には取得した値に1を加算し、存在しない場合には初期値として1をセットします。
これによって、アプリケーションにアクセスしたユーザーの人数を簡易にカウントすることができます。ただし、カウント数はファイルやデータベースにアクセスしているわけではありませんので、コンテナ(Tomcat)を再起動したタイミングで1にリセットされてしまうことに注意してください。これを防ぐためには、リスナ(Listener:後続の記事で詳述します)を使って、アプリケーション終了のタイミングでデータベースなどにあらためて記録してやる必要があります。
ここでは、getAttributeメソッドを介して取得した属性値を格納するために、ラッパクラスIntegerを用いています。
なぜ単純に基本データ型のintとして取得してはいけないのでしょう。ここではあえてわざわざIntegerクラスに変換したがために、intValueメソッドでint型に変換したり、加算した後の値を再びIntegerクラスに格納したりと、回りくどいとすら思える処理を行っています。しかし、これは「必要なこと」なのです。
getAttributeメソッドの戻り値型はObjectクラスです。Objectクラスは「すべてのクラスのスーパークラス(元となるクラス)」で、あらゆるクラス型に変換することが可能です。が、Objectクラスのようなクラス型の値を基本データ型に変換することはできないのです。で、その代替として、クラス型に属するIntegerクラスを利用するというわけです。
このように、ラッパクラスは基本データ型を暫定的にクラス型として扱いたい場合に、クラスとしての体裁を繕うラッパ(包み)として利用することができます。
ラッパクラスは、すべての基本データ型に対して用意されています。ほぼ基本データ型の名前に対応していますが、大文字小文字やスペリングが微妙に異なるものもありますので、注意してください。
以下には、基本データ型とラッパクラスの対応をリストアップしておきます。
| ラッパクラス | 対応する基本データ型 |
|---|---|
| Boolean | boolean |
| Byte | byte |
| Character | char |
| Double | double |
| Float | float |
| Integer | int |
| Long | long |
| Short | short |
なお、ラッパクラスで使える主なメソッドは以下のとおりです。ラッパクラスによる型変換の処理は煩雑ですが、コンテキスト/セッション/リクエスト属性やクッキー、コレクションなどとのhデータのやりとりに際しては頻出する操作ですので、ぜひとも押さえておきたいところです。
| メソッド名 | 概要 |
|---|---|
| Integer.parseInt(String s[, int radix]) | 文字列sをradix進数のint値に変換。radixが省略された場合には、自動的に10進数と判断される(同様に、Byte.parseByte、Double.parseDouble、Float.parseFloat、Long.parseLong、Short.parseShortメソッドなど) |
| toString | 各データ型の値を文字列に変換 |
Packageクラスは、Javaパッケージの実装・仕様に関するバージョン番号を保持します。現在の環境(正確にはクラスを管理するクラスローダ)で有効化されているパッケージに関する情報を取得したい場合には、このPackageクラスを介してアクセスすることができます。
ここでは、現在有効なパッケージの名前、バージョン、提供ベンダ名について取得してみることにします。ただし、バージョンやベンダ名については、明示的に情報を提供していないパッケージも多くあります。その場合、値はnullとなります。
<%@ page contentType="text/html;charset=Shift_JIS" %>
<table border="1">
<tr>
<th>パッケージ名</th><th>バージョン</th><th>ベンダ名</th>
</tr>
<%
Package[] aryPcg=Package.getPackages();
for(int i=0;i<aryPcg.length;i++){
%>
<tr>
<td><%=aryPcg[i].getName()%></td>
<td><%=aryPcg[i].getImplementationVersion()%></td>
<td><%=aryPcg[i].getImplementationVendor()%></td>
</tr>
<%
}
%>
</table>
Package#getPackagesメソッドは、現在の環境で有効化されているすべてのパッケージをPackageオブジェクト配列として取得します。
取得した配列に対して順番に要素を取り出し、パッケージ名・バージョン・ベンダ名を取得します。そのほか、getImplementationTitle(パッケージタイトル)、getName(パッケージ名)、getSpecificationTitle(仕様タイトル)、getSpecificationVendor(仕様を管理している組織名)、getSpecificationVersion(仕様バージョン)などの情報を得ることができます。
既存パッケージから情報を取得するばかりではありません。自作のパッケージ、アプリケーションにもあらかじめこうした属性情報を追加することが可能です。適当なテキストファイルを以下の様式で作成してください。
Implementation-Title: Y.Yamada Implementation Package Implementation-Vendor: Wings Project Implementation-Version: 1.0 Specification-Title: Y.Yamada Specification Specification-Vendor: Wings Project, JSP Sub Project Specification-Version: 1.0
このように、あらかじめ決められた様式で記述された属性情報ファイルを「マニフェストファイル」といいます。ファイル名は任意に決めることができますが、ここでは「manifest.mf」としておきましょう。
あとは「.jar」ファイル化する際に、該当するテキストファイルを引数として渡してやるだけです。マニフェストファイルを指定するには、jarコマンドの実行時に-mオプションを付加します。
> jar cmf manifest.mf sample.jar
Copyright © ITmedia, Inc. All Rights Reserved.