重新发,3月30日,第五天(上)

java学习的第五天了,本来说是1\2\4\5上课,结果老师周三又加了一天,感谢老师.

今天所讲的知识点
A 抽象类和接口的关系
B 设计模式:工厂设计模式、代理设计模式、适配器设计模式
C 匿名的内部类
D 包装类及其装箱拆箱操作
E 异常及其处理方式
F assert关键字
G 包(package)
H jar命令
I 常用的系统包
J 访问权限:public、默认(default)、protected、private
K Java的命名规范
L Eclipse开发工具


我对知识点的分析
A 抽象类和接口的区别:

No. 区别点 抽象类 接口
1 定义 用abstract关键字声明的类就是抽象类,可以没有抽象方法(老师的定义:包含有抽象方法的类?) 抽象方法和全局常量的集合
2 语法 通过abstract关键字定义 通过interface关键字定义
3 使用 抽象类通过extends被子类继承 通过implements被子类实现
4 限制 一个子类只能继承一个抽象类 一个子类可以同时实现多个接口
5 关系 一个抽象类可以实现多个接口 一个接口不能继承抽象类,只能继承接口
一个抽象类可以包含多个接口 一个接口中可以包含多个抽象类
6 设计模式 模板设计 工厂设计、代理设计
两者一起使用,可以建立适配器设计模式
7 开发 存在单继承局限 无此限制


B 在使用接口的时候,根据不同的情况,需要采用不同的设计模式:
1、工厂设计模式
当一个接口被不同的子类实现,而客户端在使用的时候直接与具体的子类相耦合了,这样不利于程序的维护,如果以后需要对子类进行修改,那么就涉及到修改客户端的应用程序,那么这样的话,就很麻烦,这个时候就可以采用工厂设计模式。
工厂设计模式就是表示在子类和客户端之间在添加一个操作类,专门来处理这些子类,这样客户端在使用的时候是通过这个中间的操作类来使用,以后需要修改子类,那么只要修改这个操作类,和客户端就没有了关系。
interface Fruit{ // 定义水果
public void eat() ; // 吃水果
}
class Apple implements Fruit{ // 定义苹果的子类
public void eat(){
System.out.println("** 吃苹果。") ;
}
};
class Orange implements Fruit{
public void eat(){
System.out.println("** 吃橘子。") ;
}
};
//原来的设计模式
public class AIDemo03{
public static void main(String args[]){
Fruit f = new Apple() ; //与子类相耦合了,如果修改或删除了苹果类,此处就不安全
f.eat() ;
}
};

//工厂设计模式
class Factory{
public static Fruit getInstance(String className){
if("apple".equals(className)){
return new Apple() ;
}
if("orange".equals(className)){
return new Orange() ;
}
return null ;
}
};
public class AIDemo04{
public static void main(String args[]){
Fruit f = Factory.getInstance(args[0]) ;
if(f!=null){
f.eat() ;
}
}
};

2、代理设计模式
当某些接口的实现,其最终要完成功能需要添加许多其他复杂的工序,而这些操作对于其各个子类又不方便直接添加,那么就可以建立一个代理类,这个代理类同样也是对这个接口的实现,只不过是添加了很多辅助方法的实现,这样其他的子类就可以通过这个代理类来完成最终的目的。
如果,在现实生活中,很多人需要租房子,而因为对当地的房源信息不清楚或者因为工作忙没时间去找房子,那么就可以通过一个代理去实现。
interface Subject{ // 定义一个操作的主题
public void findTenement () ; // 找出租房
}
class RealSubject implements Subject{
public void findTenement (){
System.out.println("租房子") ;
}
};
class ProxySubject implements Subject{
private Subject sub = null ;
public ProxySubject(Subject sub){
this.sub = sub ;
}
public void before(){
System.out.println("查找各个小区的房屋出租信息,筛选出符合条件的房源信息") ;
}
public void giveMoney(){
this.before() ;
this.sub. findTenement () ; // 交钱租房子
this.after() ;
}
public void after(){
System.out.println("") ;//处理其他的房源信息
}
};
public class AIDemo05{
public static void main(String args[]){
Subject real = new RealSubject() ;
Subject proxy = new ProxySubject(real) ;
proxy.giveMoney() ; //通过代理最终实现的找房子
}
};

3、适配器设计模式
①当一个对象需要同时实现多个接口;
interface Person{
public void sayPerson() ;
}
interface Ghost{
public void sayGhost() ;
}
class SuperMan implements Person,Ghost{
public void sayPerson(){
System.out.println("见人说人话。。。") ;
}
public void sayGhost(){
System.out.println("见鬼说鬼话。。。") ;
}
public void sayNothing(){};
};
public class AIDemo06{
public static void main(String args[]){
SuperMan sm=new SuperMan();

if(args.length!=0 &&"人".equals(args[0])){
sm.sayPerson();
}else if(args.length!=0 && "鬼".equals(args[0])){
sm.sayGhost();
}else{
sm.sayNothing();
}//*/
}

};
②或者当一个接口所具备的能力对于某些对象来说不需要全部实现,那么这个时候就可以借用一个抽象类,先实现这个接口,然后其他对象根据自己的需要从不同的方面去继承这个抽象类,这样这是个抽象类不用去也不会误被实例化,同时又解决了问题。
interface Demo{
public void funA() ;
public void funB() ;
public void funC() ;
}
abstract class DemoAdapter implements Demo{ //实现接口
public void funA(){} //空实现
public void funB(){} //空实现
public void funC(){} //空实现
};
class RealDemo extends DemoAdapter{ //继承抽象类
public void funA(){ //具体实现
System.out.println("Hello World!!!") ;
}
};
public class AIDemo07{
public static void main(String args[]){
Demo d = new RealDemo() ;
d.funA() ;
}
};
这样的两种情况都是适配器设计模式

C 当某种对接口的实现方式,只使用了一次,那么这个时候就没有必要单独定义一个类,来完成这种对接口的实现方式,而采用匿名的内部类比较好;
interface A{
public abstract void print() ;
};

class B implements A{
public void print(){
System.out.println("hello world!!!") ;
}
};
class X{
public void fun1(){
this.fun2(new B()) ; //只使用了一次B类实例化对象
}
private void fun2(A a){
a.print() ;
}
};
public class AIDemo06{
public static void main(String args[]){
new X().fun1() ;
}
};
代码可以做如此修改:
interface A{
public abstract void print() ;
};
class X{
public void fun1(){
this.fun2(new A(){ //匿名的内部类
public void print(){
System.out.println("Hello World!!!") ;
}
}) ;
}
private void fun2(A a){
a.print() ;
}
};
public class AIDemo10 {
public static void main(String args[]){
new X().fun1() ;
}
};

D Java是一种面向对象的编程语言,其设计原则是“一切皆对象”,而Java中的八种基本数据类型因为是沿用了之前面向过程的编程语言C中的基本数据类型,所以其不符合这个设计思想,那么在Java中为了解决这个问题,就为这八种基本数据类型的包装类:

No. 基本数据类型 包装类 No. 基本数据类型 包装类
1 int Integer 5 boolean Boolean
2 char Character 6 byte Byte
3 float Float 7 short Short
4 double Double 8 long Long
但是,以上的八种包装类也是分为两大类型的:
• Number:Integer、Short、Long、Double、Float、Byte都是Number的子类表示是一个数字。
• Object:Character、Boolean都是Object的直接子类。
一、基本数据类型的装箱操作
将一个基本数据类型变为包装类,这样的操作称为装箱操作。
如果要想装箱,直接使用各个包装类的构造方法即可。
• Integer的构造方法:public Integer(int value)
• Float的构造方法:public Float(float value)
• Double的构造方法:public Double(double value)
• Long的构造方法:public Long(long value)
• Short的构造方法:public Short(short value)
• Byte的构造方法:public Byte(byte value)
• Character的构造方法:public Character(char value)
• Boolean的构造方法:public Boolean(boolean value)
二、包装类的拆箱操作
将一个包装类变为一个基本数据类型,这样的操作称为拆箱操作。
所有的数值型的包装类都是Number的子类,Number类中定义了如下的拆箱操作方法:
• Integer  int:public abstract int intValue()//Number类中定义的是抽象方法,所以有abstract,而Interger等子类将其实现了
• Float  float:public abstract float floatValue()
• Double  double:public abstract double doubleValue()
• Long  long:public abstract long longValue()
• Short  short:public short shortValue()
• Byte  byte:public byte byteValue()
非数值型:
• Character char:public char charValue()
• Booleanboolean:public boolean booleanValue()
例如:
public class WrapDemo02{
public static void main(String args[]){
float temp = 10.3f ; // 基本数据类型
Float f = new Float(temp) ; // 将基本数据类型变为包装类,属于装箱操作
float y = f.floatValue() ; // 将包装类变为基本数据类型,属于拆箱操作
System.out.println(y * y) ;
}
};
 在JDK 1.4之前,所有的基本数据类型必须进行手工的装箱及拆箱操作,而且包装类本身不能直接进行四则运算,或者自增、自减的操作。
 在JDK 1.5之后,Java中增加了新的功能,可以自动装箱和拆箱。而且可以直接通过包装类进行四则运算和自增加、自减的操作。此操作的特点改进从.net平台中借鉴学来,这一点为程序的开发带来了极大的好处。
例如:
public class WrapDemo03{
public static void main(String args[]){
Float f = 10.3f ; // 自动装箱
float x = f ; // 自动拆箱
System.out.println(f * f) ; // 直接利用包装类完成
System.out.println(x * x) ; // 直接利用包装类完成
}
};

三、转型操作
(1)在各种基本数据类型的包装类中还定义了如下的构造方法,这样就实现了从字符串到各种基本数据类型的包装类的转型操作:
public Integer(String s) throws NumberFormatException:其中字符串必须是数字,否则将抛出异常
public Float(String s)throws NumberFormatException:其中字符串必须是数字(最多一个小数点),否则将抛出异常
public Double(String s)throws NumberFormatException:其中字符串必须是数字(最多一个小数点),否则将抛出异常
public Long(String s)throws NumberFormatException:其中字符串必须是数字,否则将抛出异常
public Short(String s)throws NumberFormatException:其中字符串必须是数字,否则将抛出异常
public Byte(String s)throws NumberFormatException:其中字符串必须是Unicode字符,否则将抛出异常
public Boolean(String s):如果参数为空或为true的等值情况(例如:yes),则返回true,否则返回false
(2) 在各种基本数据类型的包装类中还定义了如下的静态方法,这样就实现了从字符串到各种基本数据类型的转型操作:
public static int parseInt(String s)throws NumberFormatException
public static float parseFloat(String s)throws NumberFormatException
public static double parseDouble(String s)throws NumberFormatException
public static long parseLong(String s)throws NumberFormatException
public static short parseShort(String s)throws NumberFormatException
public static byte parseByte(String s)throws NumberFormatException
public static boolean parseBoolean(String s)
同样应该注意字符串的组成字符;
例如:
public class WrapDemo03{
public static void main(String args[]){
String str = "123.5" ; // 定义字符串由数字和一个小数点组成
float x = Float.parseFloat(str) ; // 将字符串变为float型数据
System.out.println(x * x) ;
}
};
E 计算机毕竟是机器,因为其硬件或软件的限制,对于有些情况超过了计算机的处理能力,例如,除数为零出现的无穷大的商等,像这类的操作将会导致程序的中止或者系统的崩溃,这些可能引起程序非正常运行的错误,称为异常,在Java中就提供了异常类Throwable及处理这些异常的语句结构。


一、try…catch/try…catch…finally异常处理语句处理
Exception类异常的处理格式语法如下:
try{
// 有可能发生异常的代码段
}catch(异常类型1 对象1){
// 异常的处理操作
}catch(异常类型2 对象2){
// 异常的处理操作
} ...
【finally{
// 异常的统一出口,不管是否有异常,都要执行该处的语句
}】
说明:
(1)一旦产生异常,则系统会自动产生一个异常类的实例化对象;
(2)如果程序中没有try语句或在try语句之外产生的异常,则将有系统报告错误;
(3)一旦有异常产生,在try语句之中的异常产生之后的代码也将不再执行;
(4)try语句中有异常发生时,产生的异常类的实例化对象依次与catch方法的参数进行匹配,如果匹配成功,则表示由此catch进行处理,不再继续检查之后的catch语句,如果到最后都没有与之匹配的catch语句,将交由系统报告错误;因此为了准确定位异常的位置和原因,捕获更粗的异常不能放在捕获更细的异常之前;
(5)从之前的说明图中可以看出,Exception类是所有异常的父类,那么如果将catch的参数设置成Exception类型,表示将捕获所有的异常(各异常对象将发生向上转型),所以有时候会将最后一个catch语句的参数设置为Exception类,这样当前面没有与之精确配对的参数时,都将交由此catch语句处理;
(6)在进行异常捕获及处理的时候,不要使用Throwable作为捕获的类型,因为范围太大了;
例如:
public class ExceptionDemo{
public static void main(String argsp[]){
int i = 0 ;
int j = 0 ;
System.out.println("============= 计算开始 =============") ;
int temp = 0 ; // 要在外部定义
try{
i = Integer.parseInt(argsp[0]) ; // 将第一个输入参数变为int型
j = Integer.parseInt(argsp[1]) ; // 将第二个输入参数变为int型
System.out.println("********************************") ;
temp = i / j ; // 进行除法运算
System.out.println("------------------------------------------------") ;
}catch(ArithmeticException e){
System.out.println("发生了算术异常:" + e) ; // 打印异常对象,调用toString()方法
}catch(ArrayIndexOutOfBoundsException e){
System.out.println("输入错误参数异常:" + e) ;
}catch(NumberFormatException e){
System.out.println("输入的参数不是数字异常:" + e) ;
}catch(Exception e){
//System.out.println("其他异常:" + e) ;
e.printStackTrace() ; // 打印异常信息,这种方式打印出的信息是最全的
}finally{
System.out.println("============= 计算结束 =============") ;
}
System.out.println("temp = " + temp) ;
}
};
二、Throws关键字
此关键字主要在方法的声明上使用,表示方法中不处理异常,而交给调用处处理。
例如:public static int parseInt(String s)throws NumberFormatException
如果某个方法定义的时候加了“throws 异常名称”的说明,而且该不是的异常,那么调用该方法的地方必须明确的使用try..catch进行异常的捕获处理,而不管是否真的会发生异常;
例如:
class Math{
public static int div(int i,int j) throws Exception{ // 此方法有可能出现异常
int temp = 0 ;
temp = i / j ;
return temp ;
}
};
public class WrapDemo03{
public static void main(String argsp[]){
try{//因为div()方法在声明时加了throws Exception,那么此处必须加try…catch语句处理
System.out.println(new Math().div(10,2)) ; // 此方法不管是否有异常,都需要进行处理
}catch(Exception e){
e.printStackTrace() ;
}
}
};
说明:如果在主方法上使用了thorws关键字声明的话,表示所有的异常将由JVM进行处理,实际上对于Java程序来讲,如果没有加入任何的异常处理,则默认就将由JVM进行异常的处理操作。
class Math{
public int div(int i,int j) throws Exception{ // 此方法有可能出现异常
int temp = 0 ;
temp = i / j ;
return temp ;
}
};
public class ExceptionDemo10{
public static void main(String argsp[]) throws Exception{ // 所有的异常交由JVM进行处理
System.out.println(new Math().div(10,0)) ;
}
};
三、throw关键字
throw关键字表示在程序中人为的抛出一个异常。
在程序中都会尽量的避免异常的产生,为什么还要存在throw人为的抛异常呢?
因为在设计方法的时候一般不考虑或者不直接在方法中处理异常,而是将异常交由调用方自己选择处理方式,所以在方法定义的时候加上throws关键字,而在程序try…catch语句中将捕获的异常用throw关键字直接抛出;
四、异常处理的标准格式
在实际的开发中,try、catch、finally、throw、throws五个关键字是要一起联合使用的。
例如:
class Math{
public int div(int i,int j) throws Exception{ // 此方法有可能出现异常
System.out.println("===== 计算开始 =====") ;
int temp = 0 ;
try{
temp = i / j ;
}catch(Exception e){
throw e ; // 所有异常抛出,而不直接处理
}finally{
System.out.println("===== 计算结束 =====") ;//不管是否有异常将执行该语句
}
return temp ;
}
};
public class ExceptionDemo12{
public static void main(String argsp[]){
try{
System.out.println(new Math().div(10,0)) ; // 此方法不管是否有异常,都需要进行处理
}catch(Exception e){
e.printStackTrace() ; // 打印异常信息,这种方式打印出的信息是最全的
}
}
};

你可能感兴趣的:(重新发,3月30日,第五天(上))