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,然后抛出异常。在client有一个类为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;
}
}