┏━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓ ┃.&&&& **** %%%%.  JavaScript&Javaで目指そう!基本情報技術者試験  ┃ ┃&&&&&&******%%%%%%  執筆&編集 斎藤末広 suehiro@he.mirai.ne.jp  ┃ ┃'&┃&''*┃*''%┃%'  発行    江口昌宏 ***  ┃ ┗━┻━━┻━━┻━━━━━━━━━━━━━━━━━━━━━━━━━━━┛ 広告募集:http://www2.odn.ne.jp/~egu33/jmaga/java-maga.html ┏━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓  第8号 2001/11/2x  基本情報技術者試験午後平成13年秋問12解説 ┗━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┛  プログラムを作成する上での注意事項:  Windows とIE を前提としています。  拡張子を表示するに設定してください。 ------------------------------------------------------------------------ ▼ 問12を分析  今回は,基本情報技術者試験午後平成13年秋問12のプログラムを少し直し 勉強します。  表示する文字列を漢字にします。 ------------------------------------------------------------------------ ▼ プログラム1(文字列を漢字に修正)j08-01 PriceSort.java で保存すること public class PriceSort { public static void main(String[] args) { Computer[] computers = { new Workstation( "ワークス1", 800, 256, 300000), new PersonalComputer("パソコン1", 450, 128, 180000), new Workstation( "ワークス2", 800, 512, 500000), new PersonalComputer("パソコン2", 450, 256, 200000), }; for (int i = 0; i < computers.length; i++) { System.out.println(computers[i]); } System.out.println("\n<値段順>"); PriceUtility.computeDiscountPrice(computers); PriceUtility.sort(computers); for (int i = 0; i < computers.length; i++) { System.out.println(computers[i]); } } } ------------------------------------------------------------------------ ▼ プログラム2 j08-02 IComp.java で保存すること public interface IComp { int compareWith(IComp a); } ------------------------------------------------------------------------ ▼ プログラム3(表示される文字列を漢字に修正) j08-03 Computer.java で保存すること public class Computer implements IComp { String name; int frequency; int memory; int price; public Computer(String name, int frequency, int memory, int price) { this.name = name; this.frequency = frequency; this.memory = memory; this.price = price; } public int getPrice() { return price; } public void setPrice(int price) { this.price = price; } public String toString() { return name + ", 周波数: " + frequency + ", メモリ: " + memory + ", 値段: " + price; } public double getDiscountRate() { return 0.0; } public int compareWith(IComp a) { Computer computer = (Computer)a; return computer.price - this.price; } } ------------------------------------------------------------------------ ▼ プログラム4 j08-04 Workstation.java で保存すること public class Workstation extends Computer { public Workstation(String name, int frequency, int memory, int price) { super(name, frequency, memory, price); } public double getDiscountRate() { return 0.1; } } ------------------------------------------------------------------------ ▼ プログラム5 j08-05 PersonalComputer.java で保存すること public class PersonalComputer extends Computer { public PersonalComputer(String name, int frequency, int memory, int price) { super(name, frequency, memory, price); } public double getDiscountRate() { return 0.2; } } ------------------------------------------------------------------------ ▼ プログラム6 j08-06 PriceUtility.java で保存すること public class PriceUtility { public static void computeDiscountPrice(Computer[] a) { int newPrice; for (int i = 0; i < a.length; i++) { newPrice = (int)(a[i].getPrice() * (1 - a[i].getDiscountRate())); a[i].setPrice(newPrice); } } public static void sort(IComp[] a) { // 単純挿入法による整列 int j; for (int i = 1; i < a.length; i++) { IComp temp = a[i]; for (j = i - 1; j >= 0 && temp.compareWith(a[j]) < 0; j--) { a[j + 1] = a[j]; } a[j + 1] = temp; } } } ------------------------------------------------------------------------ ▼ コンパイル&実行の仕方  上記のプログラムを同一のフォルダに保存します。例えば,c:\jworkに,j08 というフォルダを作成したとします。その場合,その j08 フォルダに保存します。  コンパイルの仕方は,Jマガ第2号を参考にしてください。jstart.bat の使い 方の説明があります。 jstart.bat を実行したら,  cd j08  javac PriceSort.java と入力します。そうすることで,6つのプログラムがいもづる式にコンパイルさ れます。 実行は,  java PriceSort です。 ------------------------------------------------------------------------ ▼ クラスの関係を表記するには  次のように,このJマガでは使用することにします。 ○ 継承の表し方  矢印を平行に2つ利用します。矢印の向きは,子クラスから親クラスへとしま す。これは,実行時に参照される道筋です。  親クラス   ↑↑  子クラス ○ 実装の表し方(implement)  矢印を一重で,線を--- で表現します。矢印の向きは,継承と同様の規則とし ます。   インターフェース ↑  クラス-------+ ○ 他のクラスの利用  矢印を直列に重ねて使用します。 クラス→→→→利用されるクラス ------------------------------------------------------------------------ ▼ 問12のクラスの関係  クラスの関係を見ていきましょう。 プログラム3より  IComp ↑  Computer ----+  Computer クラスは,IComp インタフェースを実装しています。これによって, Computer クラスにおいて,compareWith 関数を定義することになります。Computer クラスより生成されたインスタンスは,compareWith 関数より,大小関係の比較 が可能になります。 プログラム6より  PriceUtility →→→→→ IComp →→→→→ Computer  PriceUtilityクラスは,ICompインタフェース,Computerクラスを利用して, 値引き後の値段の計算,並び変えの関数を定義しています。 プログラム4,6から   Computer    ↑↑  ↑↑  Workstation, PersonalComputer  Workstation クラス,PersonalComputerクラスは,Computerクラスを継承して います。 プログラム1から  PriceSort →→→ Computer   →→→ Workstation   →→→ PersonalComputer   →→→ PriceUtility  PriceSort クラスは,Computer,Workstation,PersonalComputer,PriceUtility のクラスを利用しています。 ------------------------------------------------------------------------ ▼ プログラム1を詳細チェック  実際に実行結果を出すのは,プログラム1です。このプログラムを1行ずつ 見ていきましょう。 public class PriceSort { // 特に継承関係はなし。他のクラスを利用するのみ public static void main(String[] args) { // main 関数がプログラム動作を開始します。 Computer[] computers = { new Workstation( "ワークス1", 800, 256, 300000), new PersonalComputer( "パソコン1", 450, 128, 180000), new Workstation( "ワークス2", 800, 512, 500000), new PersonalComputer( "パソコン2", 450, 256, 200000), }; // 親クラスで配列を定義して,要素として,子クラスのインスタンスを設定 // している。 for (int i = 0; i < computers.length; i++) { System.out.println(computers[i]); } // 配列の中身を単純に表示している。println関数の引数になることによって, // coputers[i]の toString関数が利用されている。 System.out.println("\n<値段順>"); // 「値段順」と表示 PriceUtility.computeDiscountPrice(computers); // coputers 配列に対して,いっせいに値引き後の値段を計算。 PriceUtility.sort(computers); // coputers 配列の中身を整列している。整列のロジックや整列キーは,sort // 関数で定義されている。 for (int i = 0; i < computers.length; i++) { System.out.println(computers[i]); // computer 配列の中身を単純に文字列として表示する。 } } } ------------------------------------------------------------------------ ▼ 値引き後の値段,並び替え(プログラム6)をチェックしよう。  プログラム1の動作の中心である,値引き後の値段を求める関数と整列する関 数をを見てみましょう。  値引き後の値段を求める関数:computeDiscountPrice()  並び替えをする関数:sort() public class PriceUtility { public static void computeDiscountPrice(Computer[] a) { // 引数を Computer クラス型のインスタンスで受け取っている。 // Computer クラスのインスタンスは,メソッドして,getPrice(), // getDiscountRate()関数を持っている。 int newPrice; for (int i = 0; i < a.length; i++) { newPrice = (int)(a[i].getPrice() * (1 - a[i].getDiscountRate())); a[i].setPrice(newPrice); //値引き後の値段を設定 } } public static void sort(IComp[] a) { // 引数を ICompインターフェース型の変数で受け取っている。 // compareWith関数が使用可能 // 単純挿入法による整列 int j; for (int i = 1; i < a.length; i++) { IComp temp = a[i]; for (j = i - 1; j >= 0 && temp.compareWith(a[j]) < 0; j--) { a[j + 1] = a[j]; } a[j + 1] = temp; } } } ------------------------------------------------------------------------ ▼ 動作のまとめ  動作の中心は,プログラム1の PriceSort クラスです。これを中心に,継承, 実装,利用の観点からクラス同士をチェックしてみましょう。  PriceSort →→→ Computer   →→→ Workstation   →→→ PersonalComputer   →→→ PriceUtility  PriceSort クラスが,実際に動作するプログラムです。並び替えの対象のデータ として,Workstation クラス,PersonalComputer クラスを利用しています。そ のデータを入れておく配列として,Workstation クラスとPersonalComputeクラス の親クラスを利用しています。親クラスの配列を定義することで,そこに要素とし て,子クラスのインスタンスを格納しています。  データを入れた配列に対して,PriceUtility クラスを利用して,値引き計算, 整列をしています。  PriceUtility →→→→→ IComp →→→→→ Computer  値引き計算は,Computer クラスのインスタンスに対して行います。ここでは, Worksation クラスと PersonalComputer クラスを利用せずに,その親クラスであ る Computer クラスを利用することで,同じ配列の要素(Computerクラスのインス タンス)として,単純に扱っています。  整列は,IComp インターフェースを利用しています。これによって,Computer クラスの要素に対しての整列を実現してます。IComp インターフェースを利用す ることで,今後,Computer クラスだけでなく,IComp インターフェースを実装し クラスに対して,PriceUtility.sort() が利用できることになります。 ------------------------------------------------------------------------ 次号の予定  この号で,この前の秋の問題に対する解説はいったん終了します。次号は, また,初心者向けの内容にもどります。  次号は,判断文を解説します。  感想は,斎藤まで,suehiro@he.mirai.ne.jp  広告等のお問い合わせ:*** ------------------------------------------------------------------------ 著作権について  このメールマガジンで公開しているプログラムソースは,著作権を当方スタッ フが所有しますが,商用を含めて,再利用,改変,発表を制限しません。  今回のプログラムリストは,情報処理技術者試験の問題文から利用しています。 利用にあたっては,ご自分の判断でご利用ください。当方が著作権を所有してい るわけではありません。  本文に関しては,斎藤末広が著作権を所有します。再利用に関しては,承諾を 必要とします。 広告募集 http://www2.odn.ne.jp/~egu33/jmaga/java-maga.html ------------------------------------------------------------------------ ▼アンケート(以下を返信してください) この号のJマガは役立ったあるいは勉強になりましたか? 該当するものだけ残してください。 5: 大いに,YES 4: YES 3: 普通 2: NO 1: 大いに,NO その他