筆試題

1、 編寫一個類,在main方法中定義一個Map對象(採用泛型),加入若干個對象,然後遍歷並打印出各元素的key和value。

package com.itheima;

import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;

public class Test1 {

	public static void main(String[] args) {
		//定義一個key值爲String類型,value值爲Integer類型的Map集合,可用於存儲一段話中各個單詞出現次數信息
		TreeMap<String,Integer> tm=new TreeMap<String,Integer>();
		tm.put("hello", 2);
		tm.put("you", 8);
		tm.put("are", 4);
		tm.put("do", 6);
		//第一種方式遍歷TreeMap元素:keySet
		Set<String> kSet=tm.keySet();
		Iterator<String> it=kSet.iterator();
		while(it.hasNext()){
			String str=it.next();
			Integer val=tm.get(str);
			System.out.println(str+" : "+val);
		}
		System.out.println("============================");
		//第二種方式遍歷TreeMap元素:EntrySet
		Set<Map.Entry<String, Integer>> eSet=tm.entrySet();
	    Iterator<Map.Entry<String,Integer>> itor=eSet.iterator();  
		while(itor.hasNext()){  
			Map.Entry<String, Integer> me=itor.next();  
			String s=me.getKey();  
		    Integer v=me.getValue();  
		    System.out.println(s+" : "+v);
		}		
 	}
}

2、 有五個學生,每個學生有3門課(語文、數學、英語)的成績,寫一個程序接收從鍵盤輸入學生的信息,輸入格式爲:name,30,30,30(姓名,三門課成績),然後把輸入的學生信息按總分從高到低的順序寫入到一個名稱"stu.txt"文件中。要求:stu.txt文件的格式要比較直觀,打開這個文件,就可以很清楚的看到學生的信息。

package com.itheima;

/*
 * 思路:1. 定義Student對象,讓其自身具備比較性,同時複寫toString方法,方便後面寫入文件
 *     2. 將鍵盤輸入封裝成字符緩衝流,按行讀取,每一行字符串封裝成一個Student對象
 *     3. 將Student對象放到TreeSet集合中,實現按序存儲
 *     4. 將TreeSet集合中的各個Student對象寫入到stu.txt文件中
 */
import java.io.*;
import java.util.Iterator;
import java.util.TreeSet;

public class Test2 {

	public static void main(String[] args) throws Exception
	{
		BufferedReader bufr=new BufferedReader(new InputStreamReader(System.in));  
		BufferedWriter bufw=new BufferedWriter(new FileWriter("stu.txt"));
		TreeSet<Student> ts=new TreeSet<Student>();
		String line=null;
		System.out.println("請輸入學生信息,格式如name,30,30,30:");
		//將從鍵盤接收到學生信息放到一個TreeSet集合中
		while((line=bufr.readLine())!=null){
			if("over".equals(line))
				break;
			String[] strs=line.split(",");
			if(strs.length!=4){
				System.out.println("輸入信息格式不對,請重新輸入");
				continue;
			}
			ts.add(fillStu(strs));
		}
		bufr.close();
		//將TreeSet寫入到stu.txt文件中
		Iterator<Student> it=ts.iterator();
		while(it.hasNext()){
			Student stu=it.next();
			bufw.write(stu.toString());
			bufw.newLine();
		}
		bufw.flush();
		bufw.close();
	}
	//根據一個字符串數組信息填充生成Student對象
	public static Student fillStu(String[] strs){
		Student stu=new Student(strs[0],Float.parseFloat(strs[1]),Float.parseFloat(strs[2]),Float.parseFloat(strs[3]));
		return stu;
	}
}
//定義Student類,實現帶泛型的Comparable接口,讓Student對象自身具備比較性
class Student implements Comparable<Student>{

	private String name;
	private float yuWen;
	private float shuXue;
	private float yingYu;
	private float sum;
	public Student(String name, float yuWen, float shuXue, float yingYu) {
		super();
		this.name = name;
		this.yuWen = yuWen;
		this.shuXue = shuXue;
		this.yingYu = yingYu;
		this.sum=yuWen+shuXue+yingYu;
	}
	@Override
	//複寫compareTo()方法,實現Student對象按總分比較,總分一致時按姓名比較
	public int compareTo(Student o) {
        float result=this.sum-o.sum;
        if(result>0)
        	return -1;
        else if(result==0){
        	return this.name.compareTo(o.name);
        }
		return 1;
	}
	public String toString(){
		return name+", 語文成績:"+yuWen+" 數學成績:"+shuXue+" 英語成績:"+yingYu+" ---- 總分:"+sum;
	}
}

3、 自定義枚舉 Week 用於表示星期,Mon,Tue,Wed...要求每個枚舉值都有toLocaleString 方法,用於獲得枚舉所表示的星期的中文格式 星期一、星期二、星期三...

package com.itheima;

public class Test3{
	public static void main(String[] args){
		//測試實現的enum枚舉,枚舉對象的中文格式是否可以正常顯示
		Week wed=Week.Wed;
		System.out.println(wed.toLocalString());
	}
}
enum Week {
	//定義Mon,Tue,Wed...等枚舉對象,使用內部類形式實現抽象方法
	Mon {
		public String toLocalString() {
			return "星期一";
		}
	},
	Tue {
		public String toLocalString() {
			return "星期二";
		}
	},
	Wed {
		public String toLocalString() {
			return "星期三";
		}
	},
	Thu {
		public String toLocalString() {
			return "星期四";
		}
	},
	Fri {
		@Override
		public String toLocalString() {
			return "星期五";
		}
	},
	Sat {
		public String toLocalString() {
			return "星期六";
		}
	},
	Sun {
		public String toLocalString() {
			return "星期天";
		}
	};
	//定義枚舉類的抽象方法
	public abstract String toLocalString();	
}

4、 請說明Java中字符'\'的含義,有什麼作用?

package com.itheima;

/*
 * 答:1.'\'可以轉義字符,將其後面緊跟的字母或符號轉換成其它的含義。
 *     常用的轉義字符有:\n:換行,\b:退格,\r:按下回車鍵,\t:製表符,相當於tab鍵。
 *    2. 因爲'\'會轉義後面的字符,所以代碼中如果要保持\原先的意思,需要在 \前面再加一個\,表示後面的\保持原形,不轉義
 */

5、 將字符串中進行反轉。abcde --> edcba

package com.itheima;

/*
 * 思路:將待轉換的字符串先轉換成字符數組,對字符數組進行首尾互換,即實現了反轉,再將首尾互換後的字符數組封裝成字符串返回
 */

public class Test5 {

	public static void main(String[] args) {
		String str="abcdefghi";
		System.out.println(rev(str));
	}
	public static String rev(String str){
		//將字符串轉換成字符數組
		char[] chs=str.toCharArray();
		int len=str.length();
		char temp;
		//實現字符數組首尾互換
		for(int i=0;i<len/2;i++){
			temp=chs[i];
			chs[i]=chs[len-1-i];
			chs[len-1-i]=temp;
		}
		//字符數組封裝成字符串返回
		return new String(chs);
	}
}

6、 分析以下程序運行結果,說明原理。(沒有分析結果不得分)。---下面直接分析給出的代碼,原題中只有代碼,沒有任何註釋。

package com.itheima;
//分析如下:
public class Test6 {
	
    public static void main(String args[]) {
    MyThread t = new MyThread();
    //僅調用t.run()並沒有啓動線程,只是普通的函數調用
    t.run();
    //t線程啓動,開始在一個與主線程不同的線程分支運行run方法中的代碼,t線程與主線程搶奪CPU資源
    //run方法一開始就休眠,所以主線程搶到CPU時間,開始運行下面的System.out.println("A")
    t.start();
    System.out.println("A");
    }
}
class MyThread extends Thread {
    public void run() {
        try {
            Thread.sleep(3000);
            } catch (InterruptedException e) {
         }
        //休眠結束運行下面的語句
        System.out.println("B");
        }
}
/*
 程序運行結果是
 B
 A
 B
運行結果分析:
1. JVM啓動後,從main函數入口,開始執行,並創建main主線程
2. 主線程創建MyThread對象t,但t所代表的線程還沒有啓動
3. 主線程調用線程對象t的run()方法,這時還是沒有啓動t線程,只是普通的函數調用,所以程序會sleep 3秒,然後打印B
4. 主線程調用t.start(),t線程被啓動,開始有一個線程分支在運行,分支中運行的是t.run中的代碼,而main主線程仍在main函數中往下執行
5. t線程分支和main主線程開始搶奪CPU時間,因爲t線程分支中run方法中一開始就sleep 3秒,所以主線程輕而易舉地搶到執行權,繼續往下執行,
6. main函數的下一條語句是打印A,所以輸出A,這時,main主線程執行完畢
7. 主線程完畢後,t線程分支還沒休眠結束,所以console控制檯應該會停頓差不多3秒的時間,然後t線程中接着執行run方法中的剩餘語句,打印B.
 */

7、 有一個類爲ClassA,有一個類爲ClassB,在ClassB中有一個方法b,此方法拋出異常,在ClassA類中有一個方法a,請在這個方法中調用b,然後拋出異常。在客戶端有一個類爲TestC,有一個方法爲c ,請在這個方法中捕捉異常的信息。完成這個例子,請說出java中針對異常的處理機制。

package com.itheima;
/*
 * 思路:將一個int型值轉換成ASCII碼字符,如果int值超過了127,拋出異常,用這個例子來切合題目並說明java異常處理機制
 */
public class Test7 {

	public static void main(String[] args) {
		c();
	}
	//c()方法中調用A類的a()方法,OutASCIIException異常沒必要再拋給更上層調用者,直接在c()方法中捕獲並處理
	public static void c(){
		A clsA=new A();
		try {
			clsA.a();
			System.out.println("異常拋出點之後的try塊的語句不執行。。。");
		} catch (OutASCIIException e) {
			System.out.println(e.toString());
			System.out.println("錯誤的數值 是:"+e.getVal());
		}
	}
}
//A類中的a()方法調用B類的b(int)方法,對異常不做處理,直接在函數聲明中拋出,讓上層調用者處理
class A{
	public void a() throws OutASCIIException 
	{
		B clsB=new B();
		char d=clsB.b(145);
	}	
}
//B類,其中的b方法實現int值到ASCII字符的轉換,可能拋出自定義異常OutASCIIException
class B{
	public char b(int a) throws OutASCIIException{
		if(a>127)
			throw new OutASCIIException("超出了ASCII碼值的範圍,轉換成字符失敗:",a);
		return (char)a;
	}
}
//自定義異常,將一個int型值轉換成ASCII字符,當要轉換的int值超過ASCII碼取值範圍時,拋出異常
class OutASCIIException extends Exception
{
	int val;
	OutASCIIException(String msg, int val){
		super(msg);
		this.val=val;
	}
	int getVal(){
		return val;
	}	
}
/*
 * java異常處理機制:
 * java通過類的形式來描述異常,將異常封裝成對象。
 * java異常體系根節點是Throwable類,它描述了異常的共性(異常信息,引發異常的原因,可拋性等)。
 * java提供2種處理異常的方式:
 * 1. 用try...catch...finally語句處理
 *    try中存放可能出現異常的代碼,try塊中異常拋出點之後的語句不會再執行;
 *    catch捕獲異常並進行異常處理;finall中存放一定會執行的代碼,不管異常有沒有發生。
 * 2. 在函數上用throws聲明該函數可能出現的異常類,讓函數的調用者去處理該異常
                 調用者捕獲該異常後,可以繼續向上throws異常,直到拋給jvm,也可以用try...catch處理。
 */

8、 定義一個文件輸入流,調用read(byte[] b)方法將exercise.txt文件中的所有內容打印出來(byte數組的大小限制爲5)。

package com.itheima;

/*
 * 思路:因爲緩衝區數組固定是5個字節大小,而當文件中漢字時,漢字佔2個字節,一次讀取5個字節可能出現截取半個漢字的情況,所以不能急着打印;
 *     先分析一次讀取後是否截取到了半個漢字,如果是,只打印前4個字節的內容,然後退回一個字節再讀取,如果不是,直接輸出;
 *     由此想到了利用隨機訪問文件流,可以設置當前指針位置,必要時回退一個字節。
 */
import java.io.FileInputStream;
import java.io.RandomAccessFile;

public class Test8 {

	public static void main(String[] args) throws Exception
	{
		RandomAccessFile raf=new RandomAccessFile("exercise.txt","r");
		byte[] buf=new byte[5];
		int len=0;
		int currentPos=0;
		while((len=raf.read(buf))!=-1){
			String str=new String(buf,0,len);
			currentPos=currentPos+len;
			int i=0;
			//i表示一個ASCII字符字節位置或一個漢字的第一個字節位置,漢字GBK編碼的第一個字節都小於0
			while(i<5){
				if(buf[i]<0)
					i=i+2;
				else
					i=i+1;
			}
			//read(buf)後,如果截取到了半個漢字,那buf[4]肯定是一個漢字的第一個字節,buf[4]<0,上面的i=6
		    if(i==6){
		    	//截取了半個漢字時,應該退回到前一個位置,重新再讀取5個字節
		    	currentPos=currentPos-1;
			    raf.seek(currentPos);
			    //只把前4個字節的內容打印出來
			    System.out.print(str.substring(0,str.length()-1));
		    }else{
		    	//截取到完整漢字,整個輸出
			    System.out.print(str);
		    }
		}				
	}
}

9、 寫一方法,打印等長的二維數組,要求從1開始的自然數由方陣的最外圈向內螺旋方式地順序排列。 如: n = 4 則打印:

1  2  3  4
12 13 14 5
11 16 15 6
10 9  8  7                                

package com.itheima;

/*
 * 思路:1. 按螺旋的圈數進行循環,對於n階方陣,螺旋圈數是(n+1)/2.
 *     2. 每一圈都是按順時針走,順時針位置上的值依次增加,可以先循環列出向右增長的橫行和向下增長的豎列的值,剩下的半圈的值可利用對稱性得到。
 *     3. 裏面一圈的起始值是它外面一圈左側位置上的值加1
 */
public class Test9 {

	public static void main(String[] args) {
		xzArray(8);
	}
	public static void xzArray(int n){
		int[][] arr=new int[n][n];
		//如果每一圈開頭位置相鄰左側位置的值爲start,那每一圈開頭的值就是start+1,最外面一圈的start值設置爲0
		int start=0;
	    //按螺旋的圈數進行循環,給定n值的方陣,其螺旋的圈數(n+1)/2
		for(int q=0;q<(n+1)/2;q++){
			//除第一圈外,從外向裏,每一圈的開頭起始值是其左側緊鄰位置的值+1,即start+1
			if(q!=0){
				start=arr[q][q-1];
			}
		    //獲取每一圈往右增長的一行和往下增長的一列的值,每一圈的元素個數是隨着圈從外向內的層次數而變化的,用j表示,i代表每一圈向右的一行相對起始值的偏移
			for(int j=q,i=0;j<n-q&&i<=j;j++,i++){			
				arr[q][j]=start+i+1;
				//圈子越向內時,每行或每列的元素個數會減少,所以轉折的越快
				arr[j][n-1-q]=start+i+n-2*q;
			}
			//獲得每一圈往右增長的一行和往下增長的一列的值,向左增長的行數據和向上增長的列數據分別利用對稱特性行到,每對對稱位置的兩個元素加起來的值都是該層最右下角元素值的2倍。
			for(int i=q+1;i<n-q;i++){
				arr[i][q]=2*arr[n-1-q][n-1-q]-arr[q][i];
				arr[n-1-q][i]=2*arr[n-1-q][n-1-q]-arr[i][n-1-q];
			}
		}
		printArray(arr);
	}
	//打印數組的函數
	public static void printArray(int[][] arr){
		for(int i=0;i<arr.length;i++){
			for(int j=0;j<arr[i].length;j++){
				//printf實現格式化打印
				System.out.printf("%4d",arr[i][j]);
			}
			System.out.println();
		}
	}
}

10、  金額轉換,阿拉伯數字轉換成中國傳統形式。

 例如:101000001010   轉換爲   壹仟零壹拾億零壹仟零壹拾圓整

package com.itheima;

/*
 * 思路:1. 先試圖將普通的4位數及4位數以下的金額轉換成傳統漢字形式
 *     2. 任一長串金額,可以以4位爲一組進行分組,分組內金額的轉換形式與普通單獨的4位數金額一致,分組外,每個分組整合有不同的單位
 *     3. 程序可以轉換整數部分長達16位的金額,最高單位是萬億,再向上的單位暫時沒有理清,後面有機會會補充
 *     4. 考慮帶小數點的金額,轉換方法類似,相對整數部分攤簡單一些,小數可以精確到小數點後3位數,3位以後的小數沒有可用的單位,不考慮
 *     5. 阿拉伯數字與漢字大寫之間的轉換利用查表法實現
 *     
 */
public class Test10 {

	public static void main(String[] args) {
		String str="400100001010.098";
		//String str="0100";
		//System.out.println(four2Ch(str));
		num2Ch(str);
	}
	public static void num2Ch(String str){
		String[] strs=str.split("\\.");		
		int len=strs[0].length();
		StringBuilder strBuilder=new StringBuilder();
		StringBuilder strB=new StringBuilder();
		String[] bigTable={"圓","萬","億","萬億"};
		int n=0;
		//以4位爲一組,先不帶單位轉換該組爲漢字形式,然後每組再加上對應的"圓","萬","億","萬億"單位
		while(len>0){
			int start=(len-4)>0?len-4:0;
			strB=four2Ch(strs[0].substring(start, len));
			strBuilder.insert(0,strB);
			if(strB.length()==0){
				//有多個連續的零時只顯示一個
				if(!strBuilder.toString().startsWith("零")){
					strBuilder.insert(strB.length(),"零");
				}
			}else{
				strBuilder.insert(strB.length(),bigTable[n]);
			}
			n++;
			len=len-4;
		}
		if(strs.length>1){
			strBuilder.append(point2Ch(strs[1]));
		}else{
			strBuilder.append("整");
		}
		System.out.println(strBuilder.toString());
	}
	
    //將一個任意4位以內的數轉換成中國傳統貨幣形式
	public static StringBuilder four2Ch(String str){
		StringBuilder strB=new StringBuilder();
		String[] numTable={"零","壹","貳","叄","肆","伍","陸","柒","捌","玖"};
		String[] unitTable={"","拾","百","仟"};
		int len=str.length();
		char[] chArr=str.toCharArray();		
		for(int i=len-1;i>=0;i--){
			//某一位上爲0是,不顯示該位的單位
			if(chArr[i]=='0'){	
				//結尾處的0不轉換,直接去掉,除結尾外,其餘位置有連續的多個零時,只保留一個零
				if(i!=len-1&&chArr[i+1]!='0')
					strB.append("零");
			}
			//該位上值不爲0時,轉換該值爲漢字形式,並顯示其單位
			else{
				strB.append(unitTable[len-1-i]);
				strB.append(numTable[chArr[i]-48]);
			}				
		}
		return strB.reverse();
	}
	//將小數轉換成角、分、釐形式
	public static StringBuilder point2Ch(String str){
		StringBuilder strP=new StringBuilder();
		String[] pnumTable={"零","壹","貳","叄","肆","伍","陸","柒","捌","玖"};
		String[] punitTable={"角","分","釐"};
		int len=str.length();
		char[] chArr=str.toCharArray();	
		for(int i=0;i<len;i++){
			if(chArr[i]=='0'){
				if(i!=len-1&&chArr[i+1]!='0')
					strP.append("零");
			}else{
				
				strP.append(pnumTable[chArr[i]-48]);
				strP.append(punitTable[i]);
			}
		}
		return strP;
	}
}




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章