演習問題7解答例

問1 メソッドを使用
5-問1 大人と子供の判断
5-問2 正,負,及び,0 の判断
5-問3 成績の判断
5-問4 時間と分の変換
5-問5 閏年の判定
5-問8 条件付き和の計算
5-問9 個数のカウント
5-問10 直列及び並列の抵抗値
5-問14 複数人の成績の判定とその割合
5-問15 複数人の給与支払いに必要な紙幣の数(ファイル)
5-問17 数字の分離
5-問18 1 であるビット数のカウント
問2 メソッドを使用
6-問1 ベクトルの絶対値
6-問2 ベクトルの和
6-問3 内積
6-問4 データの入れ替え
6-問5 平均点の人数
6-問6 平面上の点の原点からの距離と点の数
6-問7 成分の割合(ファイル)
6-問10 売り上げの集計
6-問11 末尾の数のチェックとその割合
6-問13 平面上の点間の距離と最大
問3 メソッドを使用
5-問22 二分法
5-問23 台形則
問4 メソッドを使用
6-問16 n クラス(各クラス: m 人)の中の平均値と人数
問5 n 行 m 列の行列の和
問6 英文を構成する文字数と単語数の出力( main 関数の引数)
問7 個人データの記述
問8 3次元空間上の点の記述
問9 クラスメンバーの出力
問10 待ち行列
問11 ハッシュ表
問12 英文のリスト構造(2進木)

注:以下の問題において,基本的に,入出力を main メソッドで行い,他の処理を別のメソッドで行うように作成すること.

[問1]演習問題 5 の問 1 から問 18 までを(問 6,7,11,12,13,及び,16 を除く),メソッドを利用して書け.

[5-問1]年齢を読み込み,20 歳以上なら「大人」,そうでなければ「子供」と出力するプログラムを書け.
/****************************/
/* 大人と子どもの識別       */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int nenrei, sw;
	/*
	     年齢の入力
	*/
		System.out.print("年齢を入力してください ");
		nenrei = Integer.parseInt(in.readLine());
	/*
	     判断
	*/
		sw = (new Test()).handan(nenrei);

		if (sw > 0)
			System.out.print("   大人\n");
		else
			System.out.print("   子供\n");
	}

	/***************************/
	/* 大人か子供の判断        */
	/*      nen : 年齢         */
	/*      return : =0 : 子供 */
	/*               =1 : 大人 */
	/***************************/
	int handan(int nen)
	{
		int sw;
		sw = (nen >= 20) ? 1 : 0;
		return sw;
	}
}
		
[5-問2]一つの整数データを読み込み,その値がゼロなら「 0 」,正なら「正」,それ以外なら「負」と出力するプログラムを,if 文を使用して書け.
/****************************/
/* 正,負,ゼロの識別       */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int kazu, sw;
	/*
	     年齢の入力
	*/
		System.out.print("数字を入力してください ");
		kazu = Integer.parseInt(in.readLine());
	/*
	     判断
	*/
		sw = (new Test()).handan(kazu);

		switch (sw) {
			case 0:
				System.out.print("   0\n");
				break;
			case 1:
				System.out.print("   正\n");
				break;
			default:
				System.out.print("   負\n");
				break;
		}
	}

	/**************************/
	/* 正,負,ゼロの識別     */
	/*      kazu : 整数       */
	/*      return : =0 : 0  */
	/*               =-1 : 負 */
	/*               =1 : 正  */
	/**************************/
	int handan(int kazu)
	{
		int sw;

		if (kazu == 0)
			sw = 0;
		else {
			if (kazu > 0)
				sw = 1;
			else
				sw = -1;
		}

		return sw;
	}
}
		
[5-問3]試験の点数を読み込み,その点数が
60 点未満なら「不可」
60 点以上で 70 点未満なら「可」
70 点以上で 80 点未満なら「良」
80 点以上なら「優」
と出力するプログラムを書け
/****************************/
/* 成績の判定               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int ten, sw;
	/*
	      点数の入力
	*/
		System.out.print("点数は? ");
		ten = Integer.parseInt(in.readLine());
	/*
	      判定
	*/
		sw = (new Test()).handan(ten);

		switch (sw) {
			case 0:
				System.out.print("   不可\n");
				break;
			case 1:
				System.out.print("   可\n");
				break;
			case 2:
				System.out.print("   良\n");
				break;
			default:
				System.out.print("   優\n");
				break;
		}
	}

	/***************************/
	/* 成績の判定              */
	/*      ten : 点数         */
	/*      return : =0 : 不可 */
	/*               =1 : 可   */
	/*               =2 : 良   */
	/*               =3 : 優   */
	/***************************/
	int handan(int ten)
	{
		int sw;

		if (ten < 60)
			sw = 0;
		else {
			if (ten < 70)
				sw = 1;
			else {
				if (ten < 80)
					sw = 2;
				else
					sw = 3;
			}
		}

		return sw;
	}
}
		
[5-問4]時間と分の変換を行うプログラムを書け.つまり,1 時間 20 分なら 80 分,また,90 分なら 1 時間 30 分に変換する.
/****************************/
/* 時間の変換               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int sw;
		int time[] = new int [2];
	/*
	      変換方法の入力
	*/
		System.out.print("変換方法は(0:時間→分, 1:分→時間)? ");
		sw = Integer.parseInt(in.readLine());
	/*
	     データと変換
	*/
		if (sw == 0) {
			System.out.print("   時間は? ");
			time[0] = Integer.parseInt(in.readLine());
			System.out.print("   分は? ");
			time[1] = Integer.parseInt(in.readLine());
			(new Test()).time_cv(time, sw);
			System.out.print("      " + time[1] + " 分です\n");
		}
		else {
			System.out.print("   分は? ");
			time[1] = Integer.parseInt(in.readLine());
			(new Test()).time_cv(time, sw);
			System.out.print("      " + time[0] + " 時間 " + time[1] + " 分です\n");
		}
	}

	/*****************************/
	/* 時間の変換                */
	/*      time : 時間と分      */
	/*      sw : =0 : 時間から分 */
	/*           =1 : 分から時間 */
	/*****************************/
	void time_cv(int time[], int sw)
	{
		if (sw == 0)
			time[1] = 60 * time[0] + time[1];
		else {
			time[0] = time[1] / 60;
			time[1] = time[1] % 60;
		}
	}
}
		
[5-問5]閏年の判定を行うプログラムを書け.閏年は,年号が 4 で割り切れ,100 で割り切れない年である.ただし,400 で割り切れる年は含む.
/****************************/
/* 閏年の判定               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int year;
	/*
	     年の入力
	*/
		System.out.print("年を入力して下さい? ");
		year = Integer.parseInt(in.readLine());
	/*
	     判定
	*/
		if ((new Test()).hantei(year) > 0)
			System.out.print("   閏年です\n");
		else
			System.out.print("   閏年ではありません\n");
	}

	/******************/
	/* 閏年の判定     */
	/*      yean : 年 */
	/******************/
	int hantei(int year)
	{
		int sw;

		if (((year%4 == 0) && (year%100 != 0)) || (year%400 == 0))
			sw = 1;
		else
			sw = 0;

		return sw;
	}
}
		
[5-問8]n (入力)個のデータを読み込み,100 以上のデータ,及び,100 未満のデータの和をそれぞれ求めるプログラムを書け.
/**************************************/
/* 100以上,及び,100未満のデータの和 */
/*      coded by Y.Suganum            */
/**************************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		double sum[] = new double [2];
		int i1, n;
	/*
	     データの入力
	*/
		System.out.print("データの数は? ");
		n = Integer.parseInt(in.readLine());

		double x[] = new double [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   データは? ");
			x[i1] = Double.parseDouble(in.readLine());
		}
	/*
	     計算
	*/
		(new Test()).sum100(sum, x, n);
	/*
	     出力
	*/
		System.out.println("100未満の和 " + sum[0] + "  100以上の和 " + sum[1]);
	}

	/**************************************/
	/* 100以上,及び,100未満のデータの和 */
	/*      sum[0] : 100未満の和          */
	/*      sum[1] : 100以上の和          */
	/*      x : データ                    */
	/*      n : データの数                */
	/**************************************/
	void sum100(double sum[], double x[], int n)
	{
		int i1;
	/*
	     初期設定
	*/
		sum[0] = 0.0;
		sum[1] = 0.0;
	/*
	     計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			if (x[i1] < 100.0)
				sum[0] += x[i1];
			else
				sum[1] += x[i1];
		}
	}
}
		
[5-問9]与えられた n 個のデータ内にある正の数と負の数の個数を出力するプログラムを書け.
/***************************/
/* 正と負の数の個数        */
/*      coded by Y.Suganum */
/***************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, n;
		int ko[] = new int [2];
	/*
	     データの入力
	*/
		System.out.print("データの数は? ");
		n = Integer.parseInt(in.readLine());

		int x[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   データは? ");
			x[i1] = Integer.parseInt(in.readLine());
		}
	/*
	     数える
	*/
		(new Test()).kazu(ko, x, n);
	/*
	     出力
	*/
		System.out.println("正の数 " + ko[0] + "  負の数 " + ko[1]);
	}

	/***************************/
	/* 正と負の数の個数        */
	/*      ko[0] : 正の数の数 */
	/*      ko[1] : 負の数の数 */
	/*      x : データ         */
	/*      n : データの数     */
	/***************************/
	void kazu(int ko[], int x[], int n)
	{
		int i1;
	/*
	     初期設定
	*/
		ko[0] = 0;
		ko[1] = 0;
	/*
	     数える
	*/
		for (i1 = 0; i1 < n; i1++) {
			if (x[i1] != 0) {
				if (x[i1] > 0)
					ko[0]++;
				else
					ko[1]++;
			}
		}
	}
}
		
[5-問10]n 個の抵抗(入力)を直列または並列に接続したときの抵抗を計算するプログラムを書け.
/***************************/
/* 抵抗の直列と並列        */
/*      coded by Y.Suganum */
/***************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		double r[] = new double [2];
		int i1, n;
	/*
	     データの入力
	*/
		System.out.print("抵抗の数は? ");
		n = Integer.parseInt(in.readLine());

		double x[] = new double [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   抵抗の値は? ");
			x[i1] = Double.parseDouble(in.readLine());
		}
	/*
	     抵抗の計算
	*/
		(new Test()).teiko(r, x, n);
	/*
	     出力
	*/
		System.out.println("直列結合 " + r[0] + "  並列結合 " + r[1]);
	}

	/************************/
	/* 抵抗の直列と並列     */
	/*      r[0] : 直列結合 */
	/*      r[1] : 並列結合 */
	/*      x : データ      */
	/*      n : データの数  */
	/************************/
	void teiko(double r[], double x[], int n)
	{
		int i1;
	/*
	     初期設定
	*/
		r[0] = 0.0;
		r[1] = 0.0;
	/*
	     抵抗の計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			r[0] += x[i1];
			r[1] += 1.0 / x[i1];
		}

		r[1] = 1.0 / r[1];
	}
}
		
[5-問14]n (入力)人の試験の点を入力した後,不可,可,良,及び,優の割合(%)を計算し,出力するプログラムを書け.ただし,
不可: 50 点未満
可 : 50 点から 60 点未満
良 : 60 点から 80 点未満
優 : 80 点以上
とする.
/****************************/
/* 優、良、可、不可の割合   */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		double a[] = new double [4];
		int i1, n;
	/*
	          入力
	*/
		System.out.print("人数は? ");
		n = Integer.parseInt(in.readLine());

		int m[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   点数は ");
			m[i1] = Integer.parseInt(in.readLine());
		}
	/*
	          計算
	*/
		(new Test()).seiseki(a, m, n);
	/*
	          出力
	*/
		System.out.print("不可=" + a[0] + "%\n");
		System.out.print("  可=" + a[1] + "%\n");
		System.out.print("  良=" + a[2] + "%\n");
		System.out.print("  優=" + a[3] + "%\n");
	}

	/*********************************/
	/* 優、良、可、不可の割合        */
	/*      a : 不可,可,良,優の% */
	/*      m : データ(点数)       */
	/*      n : 人数                 */
	/*********************************/
	void seiseki(double [] a, int [] m, int n)
	{
		int i1;
	/*
	          初期設定
	*/
		for (i1 = 0; i1 < 4; i1++)
			a[i1] = 0.0;
	/*
	          計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			if (m[i1] < 50)
				a[0] += 1.;
			else {
				if (m[i1] < 60)
					a[1] += 1.;
				else {
					if (m[i1] < 80)
						a[2] += 1.;
					else
						a[3] += 1.;
				}
			}
		}

	/*
	          計算と出力
	*/
		for (i1 = 0; i1 < 4; i1++)
			a[i1] = a[i1] / n * 100.0;
	}
}
		
[5-問15]n 人に給与を支払うものとする.n 及び各人の給与の額をファイルから読み込み,すべての人に給与を釣り銭がないように支払うために必要な 10,000 円札,5,000 円札,1,000 円札,500 円硬貨,及び,100 円硬貨の合計枚数を出力するプログラムを書け.ただし,給与の最小単位は 100 円であるものとする.
/****************************/
/* 給与の計算               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new FileReader("kyuyo"));
		int i1, n;
		int m[] = new int [5];
	/*
	          データの読み込み
	*/
		n = Integer.parseInt(in.readLine());

		int kyuyo[] = new int [n];

		for (i1 = 0; i1 < n; i1++)
			kyuyo[i1] = Integer.parseInt(in.readLine());

		in.close();
	/*
	          枚数の決定
	*/
		(new Test()).maisu(m, kyuyo, n);
	/*
	          出力
	*/
		System.out.print("10000円札 " + m[0] + " 枚\n");
		System.out.print("5000円札 " + m[1] + " 枚\n");
		System.out.print("1000円札 " + m[2] + " 枚\n");
		System.out.print("500円硬貨 " + m[3] + " 枚\n");
		System.out.print("100円硬貨 " + m[4] + " 枚\n");
	}

	/*****************************************/
	/* 給与の計算                            */
	/*      m : 各枚数                       */
	/*      kyuyo : 各人の給与               */
	/*              (給与の内容変化に注意) */
	/*      n : 人数                         */
	/*****************************************/
	void maisu(int [] m, int [] kyuyo, int n)
	{
		int i1, k1;
	/*
	          初期設定
	*/
		for (i1 = 0; i1 < 5; i1++)
			m[i1] = 0;
	/*
	          計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			k1         = kyuyo[i1] / 10000;
			kyuyo[i1] -= k1 * 10000;
			m[0]      += k1;
			k1         = kyuyo[i1] / 5000;
			kyuyo[i1] -= k1 * 5000;
			m[1]      += k1;
			k1         = kyuyo[i1] / 1000;
			kyuyo[i1] -= k1 * 1000;
			m[2]      += k1;
			k1         = kyuyo[i1] / 500;
			kyuyo[i1] -= k1 * 500;
			m[3]      += k1;
			k1         = kyuyo[i1] / 100;
			m[4]      += k1;
		}
	}
}
		
[5-問17]正の整数を入力し,それを各桁毎に分解し,それらの数字を正順及び逆順に,間に 1 つ以上の空白をあけて出力するプログラムを書け.例えば,12345 と入力したら,次のように出力することになる.ただし,整数の桁数は最大 9 桁であるとする.
1 2 3 4 5
5 4 3 2 1
/****************************/
/* 数字の分離               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {
	public static void main(String args[]) throws IOException
	{
		int n;
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
					// データの入力
		System.out.print("正の整数を入力してください ");
		n = Integer.parseInt(in.readLine());
					// 分離
		(new Test()).sepa(n);
	}

	/***************************/
	/* 数字の分離              */
	/*      n : 対象となる数字 */
	/***************************/
	void sepa(int n)
	{
		int m, k = 100000000, k1, sw = 0;
					// 正順
		m = n;
		while (k > 0) {
			k1  = m / k;
			m  %= k;
			k  /= 10;
			if (k1 > 0) {
				sw = 1;
				System.out.print(k1 + " ");
			}
			else {
				if (sw > 0)
					System.out.print(k1 + " ");
			}
		}
		System.out.println();
					// 逆順
		m = n;
		while (m > 0) {
			k1  = m % 10;
			m  /= 10;
			System.out.print(k1 + " ");
		}
		System.out.println();
	}
}
		
[5-問18]整数型データの中で 1 になっているビットの数を出力するプログラムを書け.
/****************************/
/* 1のビット数を数える     */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int n;
	/*
	     整数の入力
	*/
		System.out.print("整数を入力して下さい ");
		n = Integer.parseInt(in.readLine());
	/*
	     数を数え,出力
	*/
		System.out.println("1のビット数は " + (new Test()).bit(n));
	}

	/****************************/
	/* 1のビット数を数える     */
	/*      n : 整数            */
	/****************************/
	int bit(int n)
	{
		int i1, kazu = 0;
		int mask = 0x80000000;
	/*
	     数を数える
	*/
		for (i1 = 0; i1 < 32; i1++) {
			if ((mask & n) != 0)
				kazu++;
			mask >>>= 1;
		}

		return kazu;
	}
}
		
[問2]演習問題 6 の問 1 から問 13 まで(ただし,問 8,9,及び,12 を除く)を,メソッドを利用して書け.

[6-問1]n (入力)次元のベクトル a の各要素を配列変数の各要素に入力した後,その大きさ( | a | )を出力するプログラムを書け.
/***************************/
/* ベクトルの大きさの計算  */
/*      code by Y.Suganuma */
/***************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, n;
	/*
	          データの入力
	*/
		System.out.print("ベクトルの次元は? ");
		n = Integer.parseInt(in.readLine());

		double x[] = new double [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   " + (i1+1) + " 番目の要素は? ");
			x[i1] = Double.parseDouble(in.readLine());
		}
	/*
	          計算と出力
	*/
		System.out.println("結果は=" + (new Test()).ook(n, x));
	}

	/***********************/
	/* ベクトルの大きさ    */
	/*      n : データの数 */
	/*      x : データ     */
	/***********************/
	double ook(int n, double [] x)
	{
		double s = 0.0;
		int i1;
	/*
	          計算
	*/
		for (i1 = 0; i1 < n; i1++)
			s += x[i1] * x[i1];
		s = Math.sqrt(s);

		return s;
	}
}
		
[6-問2]n (入力)次元のベクトル ab の各要素を配列変数の各要素に入力した後,ベクトル ab の和( c = a + b )を出力するプログラムを書け.
/****************************/
/* ベクトルの和の計算       */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, n;
	/*
	          入力
	*/
		System.out.print("ベクトルの次元は? ");
		n = Integer.parseInt(in.readLine());

		double [] a = new double [n];
		double [] b = new double [n];
		double [] c = new double [n];

		for (i1 = 0; i1 < n; i1=i1+1) {
			System.out.print("ベクトルaの " + (i1+1) + " 番目の要素は? ");
			a[i1] = Double.parseDouble(in.readLine());
			System.out.print("   ベクトルbの " + (i1+1) + " 番目の要素は? ");
			b[i1] = Double.parseDouble(in.readLine());
		}
	/*
	          実行
	*/
		(new Test()).add(n, a, b, c);
	/*
	          出力
	*/
		System.out.print("和は\n");
		for (i1 = 0; i1 < n; i1=i1+1)
			System.out.print(" " + c[i1]);
		System.out.print("\n");
	}

	/************************/
	/* ベクトルa,bの和c */
	/*      n : 次元        */
	/************************/
	void add(int n, double [] a, double [] b, double [] c)
	{
		int i1;
		for (i1 = 0; i1 < n; i1++)
			c[i1] = a[i1] + b[i1];
	}
}
		
[6-問3]n 次元のベクトル ab の内積を計算し出力するプログラムを書け.なお,n,および,各ベクトルの要素の値はキーボードから入力するものとする(ベクトルに対しては,配列変数を利用するものとする).また,ベクトル ab の内積 x の定義は以下の通りである.
  x = a1b1 + a2b2 + ・・・ + anbn
/****************************/
/* 内積の計算               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int n, i1;
	/*
	          データの入力
	*/
		System.out.print("次元は? ");
		n = Integer.parseInt(in.readLine());

		double a[] = new double [n];
		double b[] = new double [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   ベクトルaの " + (i1+1) + " 番目の要素は? ");
			a[i1] = Double.parseDouble(in.readLine());
		}
		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   ベクトルbの " + (i1+1) + " 番目の要素は? ");
			b[i1] = Double.parseDouble(in.readLine());
		}
	/*
	          計算と出力
	*/
		System.out.println("内積=" + (new Test()).naiseki(n, a, b));
	}

	/**********************/
	/* aとbの内積       */
	/*      n : 次元      */
	/*      return : 内積 */
	/**********************/
	double naiseki(int n, double [] a, double [] b)
	{
		double x = 0.0;
		int i1;

		for (i1 = 0; i1 < n; i1++)
			x += a[i1] * b[i1];

		return x;
	}
}
		
[6-問4]配列 a に n (入力)個のデータ,また,配列 b に n 個のデータを入力した後,もし,a[i] が b[i] より大きければ,a[i] と b[i] を入れ換える操作を行うプログラムを書け.このとき,この操作を行った回数,及び,入れ換えを行った a[i],b[i] の値を出力するものとする.
/****************************/
/* データの交換             */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, n, m;
	/*
	          入力
	*/
		System.out.print("データの数は? ");
		n = Integer.parseInt(in.readLine());

		double a[] = new double [n];
		double b[] = new double [n];

		int k[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("aの " + (i1+1) + " 番目のデータは? ");
			a[i1] = Double.parseDouble(in.readLine());
			System.out.print("   bの " + (i1+1) + " 番目のデータは? ");
			b[i1] = Double.parseDouble(in.readLine());
		}
	/*
	          実行と出力
	*/
		m = (new Test()).change(a, b, n, k);

		System.out.println("操作回数=" + m);
		for (i1 = 0; i1 < n; i1++) {
			if (k[i1] > 0)
				System.out.println("   a,b " + b[i1] + " " + a[i1]);
		}
	}

	/*********************************/
	/* データの交換                  */
	/*      a,b : データ             */
	/*      n : データの数           */
	/*      k : 交換したか否かを示す */
	/*      return : 交換回数        */
	/*********************************/
	int change(double [] a, double [] b, int n, int [] k)
	{
		double x;
		int i1, m = 0;
	/*
	          実行
	*/
		for (i1 = 0; i1 < n; i1++) {
			if (a[i1] > b[i1]) {
				x     = a[i1];
				a[i1] = b[i1];
				b[i1] = x;
				k[i1] = 1;
				m++;
			}
			else
				k[i1] = 0;
		}

		return m;
	}
}
		
[6-問5]n (入力)人の英語,及び,数学の点を入力し,各科目の平均点を計算した後(平均点も出力),どちらかの科目が平均点以下の人の数を出力するプログラムを書け.
/************************************/
/* 平均値の計算(平均点以下の出力) */
/*      coded by Y.Suganuma         */
/************************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int n, i1;
	/*
	         データの読み込み
	*/
		System.out.print("人数は? ");
		n = Integer.parseInt(in.readLine());

		int x[] = new int [n];
		int y[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print((i1+1) + " 番目の人の英語の点は? ");
			x[i1] = Integer.parseInt(in.readLine());
			System.out.print("     英語の点は? ");
			y[i1] = Integer.parseInt(in.readLine());
		}
	/*
	         結果の計算と出力
	*/
		System.out.print("平均点以下の人数は " + (new Test()).hei(x, y, n) + " 人\n");
	}

	/********************************************/
	/* 平均値の計算(平均点以下の出力)         */
	/*      x : 英語の点                        */
	/*      y : 数学の点                        */
	/*      n : 人数                            */
	/*      return : どちらかが平均点以下の人数 */
	/********************************************/
	int hei(int x[], int y[], int n)
	{
		double mean1 = 0.0, mean2 = 0.0;
		int i1, kazu = 0;
	/*
	         平均値の計算力
	*/
		for (i1 = 0; i1 < n; i1++) {
			mean1 += x[i1];
			mean2 += y[i1];
		}

		mean1 /= n;
		mean2 /= n;
	/*
	         数を数える
	*/
	   for (i1 = 0; i1 < n; i1++) {
			if (x[i1] <= mean1 || y[i1] <= mean2)
				kazu++;
		}

		return kazu;
	}
}
		
[6-問6]平面上の n 個の点の座標 ( xi, yi ) を読み込み,原点 (0, 0) からの平均距離を計算した後,平均距離,原点から平均距離以上離れたすべての点の座標,及び,その数を出力するプログラムを書け.
/****************************/
/* 原点までの距離の計算     */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		double mean[] = new double [1];
		int i1, k, n;
	/*
	         データの入力
	*/
		System.out.print("点の数は? ");
		n = Integer.parseInt(in.readLine());

		double x[] = new double [n];
		double y[] = new double [n];
		int ten[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print((i1+1) + " 番目の点のx座標は? ");
			x[i1] = Double.parseDouble(in.readLine());
			System.out.print("     y座標は? ");
			y[i1] = Double.parseDouble(in.readLine());
		}
	/*
	         計算
	*/
		k = (new Test()).gen(n, x, y, ten, mean);
	/*
	         出力
	*/
		System.out.print("平均距離は " + mean[0] + "\n点の座標は\n");
		for (i1 = 0; i1 < k; i1++)
			System.out.println(x[ten[i1]] + " " + y[ten[i1]]);
		System.out.println("   点の数=" + k);
	}

	/******************************/
	/* 平均距離以上離れた点       */
	/*      n : 点の数            */
	/*      x,y : 座標            */
	/*      ten : 離れた点の番号  */
	/*      av : 平均距離         */
	/*      return : 離れた点の数 */
	/******************************/
	int gen(int n, double x[], double y[], int ten[], double av[])
	{
		double mean = 0.0, x1;
		int i1, k = 0;
	/*
	         ワークエリア
	*/
		double z[] = new double [n];
	/*
	         距離の計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			x1     = x[i1] * x[i1] + y[i1] * y[i1];
			z[i1]  = Math.sqrt(x1);
			mean  += z[i1];
		}
	/*
	         平均距離以上離れた点の数
	*/
		mean /= n;
		for (i1 = 0; i1 < n; i1++) {
			if (z[i1] >= mean) {
				ten[k] = i1;
				k++;
			}
		}

		av[0] = mean;

		return k;
	}
}
		
[6-問7]今,ある物質を構成する n (未知数)個の成分の各質量がファイルに保存されていたとする.これらの成分を入力した後,各成分の全体に対する%を別のファイルへ出力するプログラムを書け.
/****************************/
/* 成分の%の計算           */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new FileReader("input"));
		int dim = 10, n = 0, i1;
		String str;
	/*
	         データの読み込み
	*/
		double x[] = new double [dim];

		while (null != (str = in.readLine())) {
			n++;
			if (n > dim) {
				System.out.println("データが多すぎます");
				System.exit(1);
			}
			else
				x[n-1] = Double.parseDouble(str);
		}

		in.close();
	/*
	          %の計算
	*/
		double y[] = new double [n];

		(new Test()).per(x, y, n);
	/*
	          出力
	*/
		PrintStream out = new PrintStream(new FileOutputStream("output"));

		for (i1 = 0; i1 < n; i1++)
			out.print((i1+1) + " 番目の成分 " + y[i1] + " %\n");

		out.close();
	}

	/*********************/
	/* 成分の%の計算    */
	/*      x : 成分     */
	/*      y : 成分の% */
	/*      n : 成分の数 */
	/*********************/
	void per(double [] x, double [] y, int n)
	{
		double sum = 0.0;
		int i1;
	/*
	         成分の和を計算
	*/
		for (i1 = 0; i1 < n; i1++)
			sum += x[i1];
	/*
	          %の計算
	*/
		for (i1 = 0; i1 < n; i1++)
			y[i1] = x[i1] / sum * 100.0;
	}
}
		
[6-問10]ある店舗の毎日の売上の記録 xi ( i = 1 ~ 30 )がある(入力データとして読み込む).ある与えられた日(入力データ)を基準にした前後 7 日間(例えば,5 日が与えられたときは,2 日から 8 日)の売上高の平均を計算し,出力するプログラムを書け.ただし,前後の日にちが 0 以下になったり 31 以上になった場合は,1 または 30 までの平均を計算する(例えば,2 日が与えられたときは,1 日から 5 日までの平均を計算)ものとする.また,0 以下または 31 以上の日にちが入力されたときは,再入力をうながすものとする( goto 文は使用しない).
/****************************/
/* 売上の計算               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, m = 0;
		int x[] = new int [30];
	/*
	          データの入力
	*/
		for (i1 = 0; i1 < 30; i1++) {
			System.out.print("   " + (i1+1) + " 日の売上は? ");
			x[i1] = Integer.parseInt(in.readLine());
		}

		while (m < 1 || m > 30) {
			System.out.print("基準日(1から30)は? ");
			m = Integer.parseInt(in.readLine());
		}
	/*
	          計算と出力
	*/
		System.out.println("平均=" + (new Test()).heikin(x, m));
	}

	/************************/
	/* 売上の計算           */
	/*      x : データ      */
	/*      m : 基準日      */
	/*      return : 平均値 */
	/************************/
	int heikin(int x[], int m)
	{
		int i1, k1, k2, mean = 0, n;

		k1 = m - 3;
		if (k1 < 1)
			k1 = 1;
		k2 = m + 3;
		if (k2 > 30)
			k2 = 30;
		n = k2 - k1 + 1;

		for (i1 = k1-1; i1 < k2; i1++)
			mean += x[i1];

		mean /= n;

		return mean;
	}
}
		
[6-問11]n (入力)個の正の整数値を入力し,末尾の桁が 0,1,・・・,9 のものの個数とその割合(%)を出力するプログラムを書け.
/****************************/
/* 0、1、...              */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, k1, n;
		int kk[] = new int [10];
	/*
	          初期設定
	*/
		for (i1 = 0; i1 < 10; i1++)
			kk[i1] = 0;
	/*
	          入力
	*/
		System.out.print("データの数は? ");
		n = Integer.parseInt(in.readLine());

		int m[] = new int [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   正の整数? ");
			m[i1] = Integer.parseInt(in.readLine());
		}
	/*
	          出力
	*/
		(new Test()).matu(m, kk, n);

		for (i1 = 0; i1 < 10; i1++) {
			k1 = kk[i1] * 100 / n;
			System.out.print((i1) + "  " + kk[i1] + " 個  " + k1 + " %\n");
		}
	}

	/************************/
	/* 0、1、...          */
	/*      m : データ      */
	/*      kk : 各末尾の数 */
	/*      n : データの数  */
	/************************/
	void matu(int [] m, int [] kk, int n)
	{
		int i1, k1;

		for (i1 = 0; i1 < n; i1++) {
			k1 = m[i1] % 10;
			kk[k1]++;
		}
	}
}
		
[6-問13]平面上の n (入力)個の点の座標を入力した後,すべての点の間の距離を計算し,その距離が最大になる点の組( 2 つの点の座標),及び,その距離を出力するプログラムを書け.
/****************************/
/* 点間の距離の計算         */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		double max_r;
		int n, i1;
		int k[] = new int [2];
	/*
	          データの入力
	*/
		System.out.print("点の数は? ");
		n = Integer.parseInt(in.readLine());

		double x[] = new double [n];
		double y[] = new double [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   " + (i1+1) + " 番目の点のx座標は? ");
			x[i1] = Double.parseDouble(in.readLine());
			System.out.print("     y座標は? ");
			y[i1] = Double.parseDouble(in.readLine());
		}
	/*
	          計算と出力
	*/
		max_r = (new Test()).max(x, y, n, k);

		System.out.println("点(" + x[k[0]] + "," + y[k[0]] + ")と(" +
                           x[k[1]] + "," + y[k[1]] + ")間で距離は " + max_r);
	}

	/*******************************/
	/* 点間の距離の計算            */
	/*      x,y : 点の座標         */
	/*      n : 点の数             */
	/*      k : 最大距離を与える点 */
	/*      return : 最大距離      */
	/*******************************/
	double max(double [] x, double [] y, int n, int [] k)
	{
		double max_r = 0.0, r, r1, r2;
		int i1, i2;

		for (i1 = 0; i1 < n-1; i1++) {
			for (i2 = i1+1; i2 < n; i2++) {
				r1 = x[i1] - x[i2];
				r2 = y[i1] - y[i2];
				r  = Math.sqrt(r1 * r1 + r2 * r2);
				if (r > max_r) {
					max_r = r;
					k[0]  = i1;
					k[1]  = i2;
				}
			}
		}

		return max_r;
	}
}
		
[問3]演習問題 5 の問 22 と問 23 を,メソッドを利用して書け.ただし,f(x) の計算を別のメソッドで行い,f(x) が変化しても,二分法及び台形則による積分を実行するメソッドを変更しなくて済むように書け.

[5-問22]二分法により次式の根を求めるためのプログラムを書け.
f(x) = ex - 3x = 0
ただし,二分法は,関数 f(x) が区間 [a, b] で連続で,かつ,根が 1 つだけ存在するとき利用できる方法である.従って,f(a)f(b) < 0となる.区間 [a, b] の中点 c を
c = 0.5 * (a + b)
で求め,f(c) の値を計算し,f(a)f(c) < 0なら
b = c,f(b) = f(c)
そうでなければ
a = c,f(a) = f(c)
と置き換え,根の存在区間を半分に縮小する.この操作を,
|b - a| < ε
が満足されるまで繰り返すことによって解を求める.

プログラム例 11.2 を参照してください.

[5-問23]台形則により次の関数の任意区間の積分値を計算するプログラムを書け.
f(x) = (2π)-0.5-x*x/2
ただし,台形則は,積分区間 [x1, x2] を n 個の,幅
h = (x2 - x1) / n
の小区間に分け,各区間の面積を右図のような台形で近似して,積分値を計算する方法である.従って,積分値 S は次のように書ける.
  S = 0.5h{f(x1) + 2(f(x1+h) + f(x1+2h) + ・・・ + f(x2-h)) + f(x2)}

プログラム例 11.9 を参照してください.

[問4]演習問題 6 の問 16 を,メソッドを利用して書け.

[6-問16]ある学年に n (入力)クラスあり,各クラスには m 人(入力,クラス毎に異なる)の生徒がいるものとする.全員に対しある試験を実施したとき,各人の名前,点数を配列に保存した後,学年平均点以下の人の名前とその点数を出力するプログラムを書け.
/*******************************/
/* 平均点と平均点以下の人(new) */
/*      coded by Y.Suganuma    */
/*******************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, i2, n;
	/*
	     データの入力と平均点の計算
	*/
		System.out.print("クラスの数は? ");
		n = Integer.parseInt(in.readLine());

		int cl[][] = new int [n][0];
		int m[] = new int [n];
		String name[][] = new String [n][0];

		for (i1 = 0; i1 < n; i1++) {

			System.out.print((i1+1) + " 番目のクラスの人数は ");
			m[i1]    = Integer.parseInt(in.readLine());

			cl[i1]   = new int [m[i1]];
			name[i1] = new String [m[i1]];

			for (i2 = 0; i2 < m[i1]; i2++) {
				System.out.print("     " + (i2+1) + " 番目の人の名前は? ");
				name[i1][i2] = in.readLine();
				System.out.print("        " + (i2+1) + " 番目の人の点は? ");
				cl[i1][i2] = Integer.parseInt(in.readLine());
			}
		}
	/*
	     出力
	*/
		(new Test()).heikin(cl, m, n);

		for (i1 = 0; i1 < n; i1++) {
			for (i2 = 0; i2 < m[i1]; i2++) {
				if (cl[i1][i2] <= 0)
					System.out.println("   " + (-cl[i1][i2]) + " 点  " + name[i1][i2]);
			}
		}
	}

	/*********************************************************/
	/* 平均点と平均点以下の人(calloc)                        */
	/*      cl[i][j] : i番目のクラスのj番目の人の点        */
	/*                  (平均点以下の場合は,負にして返す) */
	/*      m[i] : i番目のクラスの人数                      */
	/*      n : クラスの数                                   */
	/*********************************************************/
	void heikin(int [][] cl, int [] m, int n)
	{
		int i1, i2, mean = 0, nin = 0;
	/*
	     平均点の計算
	*/
		for (i1 = 0; i1 < n; i1++) {
			nin += m[i1];
			for (i2 = 0; i2 < m[i1]; i2++)
				mean += cl[i1][i2];
		}

		mean /= nin;
	/*
	     比較
	*/
		for (i1 = 0; i1 < n; i1++) {
			for (i2 = 0; i2 < m[i1]; i2++) {
				if (cl[i1][i2] <= mean)
					cl[i1][i2] = -cl[i1][i2];
			}
		}
	}
}
		
[問5]n 行 m 列の行列の足し算を行うプログラムを,メソッドを利用して書け.なお,メソッドは,任意の n 及び m に対応できるようにせよ.
/****************************/
/* 行列の足し算(new)        */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

public class Test {

	public static void main(String args[]) throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		int i1, i2, n, m;
	/*
	     データの入力
	*/
		System.out.print("行の数は? ");
		n = Integer.parseInt(in.readLine());
		System.out.print("列の数は? ");
		m = Integer.parseInt(in.readLine());

		double a[][] = new double [n][m];
		double b[][] = new double [n][m];
		double c[][] = new double [n][m];

		System.out.print("行列a\n");
		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   " + (i1+1) + "行目\n");
			for (i2 = 0; i2 < m; i2++) {
				System.out.print("      " + (i2+1) + "列目のデータは? ");
				a[i1][i2] = Double.parseDouble(in.readLine());
			}
		}

		System.out.print("行列b\n");
		for (i1 = 0; i1 < n; i1++) {
			System.out.print("   " + (i1+1) + "行目\n");
			for (i2 = 0; i2 < m; i2++) {
				System.out.print("      " + (i2+1) + "列目のデータは? ");
				b[i1][i2] = Double.parseDouble(in.readLine());
			}
		}
	/*
	     計算と出力
	*/
		(new Test()).add(a, b, c, n, m);

		for (i1 = 0; i1 < n; i1++) {
			for (i2 = 0; i2 < m; i2++)
				System.out.print(c[i1][i2] + " ");
			System.out.print("\n");
		}
	}

	/**********************************/
	/* n行m列の行列の足し算(calloc) */
	/*      c = a + b                 */
	/**********************************/
	void add(double [][] a, double [][] b, double [][] c, int n, int m)
	{
		int i1, i2;

		for (i1 = 0; i1 < n; i1++) {
			for (i2 = 0; i2 < m; i2++)
				c[i1][i2] = a[i1][i2] + b[i1][i2];
		}
	}
}
		
[問6]キーボードから,「 English This is a pen 」 のように English の後に英文を入力すると,英文を構成する単語数及びすべての文字数を出力するプログラムを main メソッドの引数を利用して書け.
/******************************************/
/* 入力された単語と文字数を数えるコマンド */
/*      coded by Y.Suganuma               */
/******************************************/
import java.io.*;

public class Test {

	public static void main(String args[])
	{
		int i1, num = 0;

		for (i1 = 0; i1 < args.length; i1++)
			num += args[i1].length();

		System.out.println("単語数は " + args.length + " 文字数は " + num);
	}
}
		

[問7]名前( char ),給与( int ),及び,年齢( int )をクラスで表現し,そこへ入出力を行うプログラムを書け.
/****************************/
/* 名前,給与,年齢         */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスTestの定義
class Test {
	private String name;
	private int kyuyo, nenrei;
					// 入力
	void input() throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		System.out.print("名前は? ");
		name = in.readLine();
		System.out.print("給与は? ");
		kyuyo = Integer.parseInt(in.readLine());
		System.out.print("年齢は? ");
		nenrei = Integer.parseInt(in.readLine());
	}
					// 出力
	void print()
	{
		System.out.print("名前 " + name);
		System.out.print(" 給与 " + kyuyo);
		System.out.println(" 年齢 " + nenrei);
	}
}
					// main
public class Test1 {
	public static void main(String args[]) throws IOException
	{
		Test x = new Test();
		x.input();
		x.print();
	}
}
		
[問8]n (入力)個の 3 次元空間の点の座標を入力した後,原点からの平均距離を計算し,平均距離以上離れた点の個数を出力するプログラムを,クラスを使用して書け.
/****************************/
/* 3次元空間の点           */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスTestの定義
class Test {
	private double x, y, z;
	double r;
						// 点の座標の入力
	void input() throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		System.out.print("   点の座標は(x)? ");
		x = Double.parseDouble(in.readLine());
		System.out.print("   点の座標は(y)? ");
		y = Double.parseDouble(in.readLine());
		System.out.print("   点の座標は(z)? ");
		z = Double.parseDouble(in.readLine());
	}
						// 原点までの距離の計算
	void range()
	{
		r = Math.sqrt(x*x + y*y + z*z);
	}
}
					// main
public class Test1 {
	public static void main(String args[]) throws IOException
	{
		double mean = 0.0;
		int i1, kosu = 0, n;
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
						// 入力
		System.out.print("点の数は? ");
		n = Integer.parseInt(in.readLine());

		Test p[] = new Test [n];   // C++との違いに注意してください
		for (i1 = 0; i1 < n; i1++)
			p[i1] = new Test ();

		for (i1 = 0; i1 < n; i1++) {
			p[i1].input();
			p[i1].range();
			mean += p[i1].r;
		}
						// 点の個数
		mean /= n;

		for (i1 = 0; i1 < n; i1++) {
			if (p[i1].r >= mean)
				kosu++;
		}

		System.out.print("      平均距離 " + mean);
		System.out.println(" 個数は " + kosu);
	}
}
		
[問9]名前,住所,電話番号をクラスを使用して記述し,名前を入力すると電話番号を出力するプログラムを書け.
/****************************/
/* 名前,住所,電話番号     */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスTestの定義
class Test {
	private String name;
	private String jusho;
	private String tel;
						// 入力
	void input() throws IOException
	{
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
		System.out.print("   名前は? ");
		name = in.readLine();
		System.out.print("   住所は? ");
		jusho = in.readLine();
		System.out.print("   電話番号は? ");
		tel = in.readLine();
	}
						// 探索
	String search(String na)
	{
		if (name.equals(na))
			return tel;
		else
			return null;
	}
}
					// main
public class Test1 {
	public static void main(String args[]) throws IOException
	{
		String c, name;
		int i1, n, sw = 1;
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
	/*
	     入力(データベースの作成)
	*/
		System.out.print("人数は? ");
		n = Integer.parseInt(in.readLine());

		Test p[] = new Test [n];

		for (i1 = 0; i1 < n; i1++) {
			System.out.println();
			p[i1] = new Test();
			p[i1].input();
		}
	/*
	     探索
	*/
		System.out.println("探索");

		while (sw > 0) {
			System.out.print("   名前は?(endで終了) ");
			name = in.readLine();
			if (!name.equals("end")) {
				for (i1 = 0; i1 < n && sw != 0; i1++) {
					c = p[i1].search(name);
					if (c != null) {
						System.out.println("      電話番号は " + c);
						sw = 0;
					}
				}
				if (sw != 0)
					System.out.println("      見つかりません");
				sw = 1;
			}
			else
				sw = 0;
		}
	}
}
		
[問10]最大待ち行列長を 10 として,待ち行列をクラスで表現するプログラムを書け.ただし,待ち行列は,配列に待ち行列に入っている要素-数字-を格納することによって表すものとする.メソッドとしては,待ち行列に要素を入れるメソッド put(int num),待ち行列から要素を取り出すメソッド get(),及び,待ち行列の状態を出力するメソッド qprint() を用意せよ.
/****************************/
/* 待ち行列                 */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスTestの定義
class Test {
	private int que[];
	private int size;
	private int now;
						// コンストラクタ
	Test(int n)
	{
		size = n;
		now  = 0;
		que  = new int [n];
	}
						// 待ち行列に追加
	void put(int num)
	{
		now++;
		if (now > size) {
			System.out.println("***error  待ち行列オーバーフロー");
			System.exit(1);
		}
		que[now-1] = num;
	}
						// 待ち行列から取り除く
	int get()
	{
		int i1, num = 0;
		if (now > 0) {
			num = que[0];
			for (i1 = 1; i1 < now; i1++)
				que[i1-1] = que[i1];
			now--;
		}
		return num;
	}
						// 待ち行列の状態を出力
	void qprint()
	{
		int i1;
		System.out.print("   数 " + now);
		if (now > 0) {
			System.out.print(" 内容");
			for (i1 = 0; i1 < now; i1++)
				System.out.print(" " + que[i1]);
		}
		System.out.println();
	}
}
						// main
public class Test1 {
	public static void main(String args[])
	{
		Test q = new Test (2);

		System.out.println("3を追加");
		q.put(3);
		q.qprint();
		System.out.println("1を追加");
		q.put(1);
		q.qprint();
		System.out.println("先頭を取り除く");
		q.get();
		q.qprint();
		System.out.println("2を追加");
		q.put(2);
		q.qprint();
		System.out.println("5を追加");
		q.put(5);
		q.qprint();
	}
}
		
[問11]レコードの格納と取り出しを文字列キーで行うハッシュ表のクラスを書け.その際,レコードの挿入,探索,及び,削除を行うメソッドも用意せよ.
/****************************/
/* ハッシュテーブル         */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスRecord
class Record {
	String data;
						// コンストラクタ
	Record(String str)
	{
		data = new String (str);
	}
}
					// クラスClist(衝突リスト)
class Clist {
	Record r;
	Clist next;
						// コンストラクタ
	Clist () { next = null; }
}
					// クラスTest(ハッシュテーブル)
class Test {
	private int size;                    // ハッシュテーブルの大きさ
	private Clist table[];               // 衝突リスト
						// ハッシュ関数
	int hash(String s) throws UnsupportedEncodingException
	{
		int hash = 0, g;
		int i1, len;
		byte bs[] = s.getBytes("ASCII");

		len = bs.length;
		for (i1 = 0; i1 < len; i1++ ) {
			hash = (hash << 4) + bs[i1];   // 左に4ビットシフトし文字を加える
			g    = hash & 0xf0000000;   // ビット毎のAND
			if (g != 0) {
				hash ^= g >> 24;   // 排他的論理和
				hash ^= g;
			}
		}

		return hash % size;
	}
						// コンストラクタ
	Test(int sz)
	{
		int i1;
		size  = sz;
		table = new Clist [size];
		for (i1 = 0; i1 < size; i1++)
			table[i1] = null;
	}
						// レコードの探索
						//   成功:レコードへのポインタ,失敗:0
	Record search(String str) throws UnsupportedEncodingException
	{
		Clist p;
		for (p = table[hash(str)]; p != null; p = p.next) {
			if (str.equals(p.r.data))
				return p.r;
		}
		return null;
	}
						// レコードの追加
						//   成功:レコードへのポインタ,失敗:0
	Record add(Record rec) throws UnsupportedEncodingException
	{
		if (search(rec.data) != null)     // 既に存在
			return null;
		else {                            // 付加
			int i    = hash(rec.data);
			Clist p  = new Clist ();
			p.r      = rec;
			p.next   = table[i];
			table[i] = p;
			return rec;
		}
	}
						// レコードの削除
						//   成功:レコードへのポインタ,失敗:0
	Record remove(String str) throws UnsupportedEncodingException
	{
		int i    = hash(str);
		Clist p = table[i];
		Clist q = null;

		while ((p != null) && !str.equals(p.r.data)) {
			q = p;
			p = p.next;
		}

		if (p != null) {
			if (q != null)
				q.next = p.next;
			else
				table[i] = p.next;
			Record r = new Record (p.r.data);
			return r;
		}
		else
			return null;
	}
}
						// main
public class Test1 {
	public static void main(String args[]) throws UnsupportedEncodingException
	{
		Test H = new Test (100);
		Record rec1 = new Record("test1");
		Record rec2 = new Record("test2");
							// データ "test1", "test2" の追加
		Record p1 = H.add(rec1);
		Record p2 = H.add(rec2);
		if (p1 != null)
			System.out.println("データ " + p1.data + " の追加");
		if (p2 != null)
			System.out.println("データ " + p2.data + " の追加");
							// データ "test1" の削除
		System.out.println("データ test1 の削除");
		p1 = H.remove("test1");
							// データの検索
		System.out.println("データ test1 の検索");
		p1 = H.search("test1");
		if (p1 == null)
			System.out.println("   データ test1 は見つかりません");
		System.out.println("データ test2 の検索");
		p2 = H.search("test2");
		if (p2 != null)
			System.out.println("   データ " + p2.data + " は見つかりました");
	}
}
		
  上のプログラムは,String からハッシュコードを生成する String クラスのメソッド hashCode を使用して以下のように書いても構いません.ただし,hashCode によるハッシュコードの生成方法は以下の通りです.

s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1]
/****************************/
/* ハッシュテーブル         */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;
					// クラスRecord
class Record {
	String data;
						// コンストラクタ
	Record(String str)
	{
		data = new String (str);
	}
}
					// クラスClist(衝突リスト)
class Clist {
	Record r;
	Clist next;
						// コンストラクタ
	Clist () { next = null; }
}
					// クラスTest(ハッシュテーブル)
class Test {
	private int size;                    // ハッシュテーブルの大きさ
	private Clist table[];               // 衝突リスト
						// ハッシュ関数
	int hash(String s)
	{
		return s.hashCode() % size;
	}
						// コンストラクタ
	Test(int sz)
	{
		int i1;
		size  = sz;
		table = new Clist [size];
		for (i1 = 0; i1 < size; i1++)
			table[i1] = null;
	}
						// レコードの探索
						//   成功:レコードへのポインタ,失敗:0
	Record search(String str)
	{
		Clist p;
		for (p = table[hash(str)]; p != null; p = p.next) {
			if (str.equals(p.r.data))
				return p.r;
		}
		return null;
	}
						// レコードの追加
						//   成功:レコードへのポインタ,失敗:0
	Record add(Record rec)
	{
		if (search(rec.data) != null)     // 既に存在
			return null;
		else {                            // 付加
			int i    = hash(rec.data);
			Clist p  = new Clist ();
			p.r      = rec;
			p.next   = table[i];
			table[i] = p;
			return rec;
		}
	}
						// レコードの削除
						//   成功:レコードへのポインタ,失敗:0
	Record remove(String str)
	{
		int i    = hash(str);
		Clist p = table[i];
		Clist q = null;

		while ((p != null) && !str.equals(p.r.data)) {
			q = p;
			p = p.next;
		}

		if (p != null) {
			if (q != null)
				q.next = p.next;
			else
				table[i] = p.next;
			Record r = new Record (p.r.data);
			return r;
		}
		else
			return null;
	}
}
						// main
public class Test1 {
	public static void main(String args[])
	{
		Test H = new Test (100);
		Record rec1 = new Record("test1");
		Record rec2 = new Record("test2");
							// データ "test1", "test2" の追加
		Record p1 = H.add(rec1);
		Record p2 = H.add(rec2);
		if (p1 != null)
			System.out.println("データ " + p1.data + " の追加");
		if (p2 != null)
			System.out.println("データ " + p2.data + " の追加");
							// データ "test1" の削除
		System.out.println("データ test1 の削除");
		p1 = H.remove("test1");
							// データの検索
		System.out.println("データ test1 の検索");
		p1 = H.search("test1");
		if (p1 == null)
			System.out.println("   データ test1 は見つかりません");
		System.out.println("データ test2 の検索");
		p2 = H.search("test2");
		if (p2 != null)
			System.out.println("   データ " + p2.data + " は見つかりました");
	}
}
		
[問12]英語の単語を入力し,それを 2 進木として記憶するプログラムをクラスを利用して書け.ただし,新しい単語が入力されたとき,記憶されている単語よりアルファベット順で前にあるなら左,そうでなければ右の枝をたどるものとする.例えば,11 個の単語が,「 network parameters are optimized from empirical data and the optimal number 」 という順に入力された場合は以下のようになる.
/****************************/
/* リスト処理               */
/*      coded by Y.Suganuma */
/****************************/
import java.io.*;

/**************/
/* クラスTest */
/**************/
class Test {
	private String name;
	private Test mae;
	private Test ato;
	static Test head = null;

	/******************/
	/* コンストラクタ */
	/******************/
	Test()
	{
		mae  = null;
		ato  = null;
	}

	/**********************************************/
	/* 単語の探索                                 */
	/*   tango : 入力された単語                   */
	/*   base : 単語が入っているオブジェクト      */
	/*   same : =0 : 単語を追加                   */
	/*          =1 : 既に同じ単語がリスト上にある */
	/*   return : 追加するオブジェクト            */
	/**********************************************/
	Test search(String tango, Test base, int same[])
	{
		Test add_a;
		int sw;
		same[0] = 0;
	/*
	     単語の比較
	*/
		sw = tango.compareTo(base.name);
					// 同じ単語
		if (sw == 0) {
			same[0] = 1;
			return base;
		}
					// 異なる単語
		else {
			if (sw < 0) {   // 左
				if (base.mae == null) {
					add_a    = new Test();
					base.mae = add_a;
				}
				else
					add_a = search(tango, base.mae, same);
			}
			else {   // 右
				if (base.ato == null) {
					add_a    = new Test();
					base.ato = add_a;
				}
				else
					add_a = search(tango, base.ato, same);
			}
			return add_a;
		}
	}

	/*****************************************/
	/* 単語の追加                            */
	/*   tango : 入力された単語              */
	/*   base : 単語が入っているオブジェクト */
	/*****************************************/
	void add(String tango, Test base)
	{
		base.name = new String (tango);
	}

	/***************************************************/
	/* 単語の出力                                      */
	/*   base : 対象とする単語が入っているオブジェクト */
	/*   dep : リストの深さ                            */
	/***************************************************/
	void output(Test base, int dep)
	{
		int i1;
		if (base != null) {
			for (i1 = 0; i1 < dep; i1++)
				System.out.print("   ");
			System.out.println(base.name);
			dep++;
			output(base.mae, dep);
			output(base.ato, dep);
		}
	}
}

/********/
/* main */
/********/
public class Test1 {
	public static void main(String args[]) throws IOException
	{
		Test tree = new Test ();
		Test add_a;
		int sw = 1;
		int same[] = new int [1];
		String tango;
		BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
	/*
	     単語の入力とリストの作成
	*/
		while (sw != 0) {
						// 単語入力
			System.out.print("単語を入力して下さい(終了はピリオド) ");
			tango = in.readLine();
						// 終了判定とリスト作成
			if (!tango.equals(".")) {
				if (Test.head == null) {   // 最初の単語
					tree.add(tango, tree);   // 追加
					Test.head = tree;
				}
				else {
					add_a = tree.search(tango, Test.head, same);   // 探索
					if (same[0] == 0)
						tree.add(tango, add_a);   // 追加
				}
			}
			else
				sw = 0;
		}
	/*
	     リストの出力
	*/
		tree.output(Test.head, 0);
	}
}
		

菅沼ホーム 演習解答例目次 本文目次 付録 索引