.<_java入门基础知识笔记">
赞
踩
创建对象的过程:
JavaBean是Java写成的可重用组件
符合以下标准的Java类:称之为JavaBean:
修饰符 | 同一个类中 | 同一个包中子类无关类 | 不同包的子类 | 不同包的无关类 |
---|---|---|---|---|
private | √ | |||
默认 | √ | √ | ||
protected | √ | √ | √ | |
public | √ | √ | √ | √ |
表示该类的属性变量:this.变量名
调用本类的构造方法:this()
表示当前类,可调用成员方法:this.成原方法名()
调用类的构造器(构造方法)
<权限修饰符> 构造器名() {
}
构造器和方法的区别:
构造器的作用
为类的属性赋值(无参构造器或构造器的重载)
格式:
a instanceof A:判断对象a是否使A的实例。返回值为bool型(是返回true)
用法:
可避免向下转型时出现ClassCastException的异常,即先判断返回true再进行转型。
(换言之,可以对某个对象进行选择性的转型)
访问父类的成员变量:super.变量名
关键字 | 访问成员变量 | 访问构造方法 |
---|---|---|
this | this.成员变量 访问本类成员变量 | this() 访问本类构造方法 |
super | super.成员变量 访问父类成员变量 | super() 访问父类构造方法 |
通过子类对象访问一个方法
子类中所有构造方法被调用时,默认都会先访问父类无参构造方法
方法重写
子类出现了和父类中一模一样的方法声明
应用
当子类需要父类的功能,而功能的主体子类又自己特有的内容时,可重写父类中的方法,这样即沿袭了父类的功能,又定义了子类特有的内容。
重写的方法中,可擅用super关键字沿袭父类的(基础)功能
课用@Override检测重写方法是否有误
注意事项
父类中的private方法无法被子类继承,则无法被重写
子类方法访问权限不能更低
(public>默认>protected>private)
Java继承的注意事项
在Java中主要有两种体现形式:
成员访问特点:(为何两种不一样:成员方法有重写)
优弊
优势:提高了程序的扩展性
具体体现:定义方法的时候,使用父类型作为参数,将来在使用的时候,使用具体的子类型参与操作
弊端:不能使用子类的特有功能
转型(实现使用子类特有功能)
向上转型:从子到父,父类引用指向对象
向下转型:从父到子,父类引用转为子类对象
用强制类型转换实现执行子类特有方法(不占用新的堆内存)
概述:
在Java中,一个没有方法体的方法应该定义为抽象方法,而类中如果有抽象方法,该类必须定义为抽象方法
特点
抽象类和抽象方法必须用abstract关键字修饰
抽象类中不一定有抽象方法,由抽象方法的类一定时抽象类
抽象类不能直接实例化
如何实例化:参照多态的方法,通过子类对象实例化,这叫做抽象类多态
抽象类的子类
要么重写抽象类中的所有抽象方法
要么本身就是抽象类
抽象类成员特点
成员变量:变量/常量
构造方法:
不可直接实例化。
用于子类访问父类数据的初始化
成员方法:
可以有抽象方法:限定子类必须完成某些动作
也可以有非抽象方法:提高代码的复用性
抽象类名作为形参和返回值
Java中的接口更多的体现在对行为的抽象
声明接口关键字:interface
public interface <接口名>;
调用接口关键字:implements
public class A implements <接口名>;
接口是abstract的,亦不可直接实例化
接口多态
成员特点
构造方法
接口无构造方法,因为接口主要是行为进行抽象的
一个类如果无父类,默认继承自Object类
类和接口的关系
一个类或接口可以implements多个接口
抽象类和接口的关系
成员区别
抽象类 | 变量,常量;有构造方法;有抽象方法也有非抽象方法 |
---|---|
接口 | 常量;抽象方法 |
2.关系区别
类与类 | 只能extends一个父类 |
---|---|
类与接口 | 可以implements多个接口 |
接口与接口 | 同上 |
3.设计理念区别
抽象类 | 对象抽象(属性,行为) |
---|---|
接口 | 主要对行为抽象 |
接口名作为形参和返回值
JDK8接口的新特性
JDK7及以前,只能定义全局常量和抽象方法(参见4.)
JDK8以后,接口还可以定义静态(static)方法和默认(default)方法。
接口中定义的静态方法,只能通过接口调用
如
interface IA() { public static method() {} } public SubClass implements IA {} public Class SubClassTest { public static void main(String[] args) { SubClass s = new SubClass(); s.method(); // × SubClass.method(); // × //上述两种调用方法,(编译时?)会完全无视method方法 IA.method(); // √ } }
接口中的默认方法,可通过实现类的对象调用。
如果子类(或实现类)继承的父类和实现的接口中声明了同名同参的方法,那么子类在没有重写此方法的情况下,默认调用的是父类中的同名同参的方法(类优先原则)
如果实现类实现了多个含有同名同参的默认方法的接口,且实现类没有重写此方法的情况下,会报错(接口冲突)(必须重写此方法才可以使用)
在子类(实现类)调用接口中的方法
class SuperClass() { public void method(); } interface CompareA() { public static void staticMethod(){} public void method(); } class SubClass extends SuperClass implements CompareA() { public void method(); public void myMethod() { method();//调用自己定义的重写的方法 super.method();//调用父类中声明的方法 CompareA.staticMethod();//调用接口中的静态方法 CompareA.super.method();//调用接口中的默认类型方法 } }
访问特点
成员内部类
当内部类权限为public时:
外界使用内部类格式(外部类名.内部类名):
例:Outer.Inner oi = new Outer().new Inner();
当内部类权限为private时:
类似于构建getAge和setAge方法。
局部内部类
定义在方法内,外界无法直接访问,需要在方法内部创建对象并使用
该类可直接访问外部类的成员,也可访问方法内的局部变量
匿名内部类
前提:存在一个类或接口,类可以时具体类也可抽象类
格式:
new 类名或接口名() {
重写方法;
}
本质:
是一个继承了该类或实现了该接口的子类匿名对象
用例:
不用匿名内部类
interface A { public void printlnfo(); } class B implements A { //定义接口实现类 public void printlnfo() { //重写抽象方法 System.out.println("Hello World!"); } } class X { public void fun1() { this.fun2(new B()); } public void fun2(A a) { a.printlnfo(); } } public class NoInnerClassDemo01 { public static void main(String[] args) { new X().fun1(); } }
使用内部类改写:省去写新的实现接口的类
interface A { public void printlnfo(); } class X { public void fun1() { this.fun2(new A() { //匿名内部类 public void printlnfo() { //实现接口内中的抽象方法 System.out.printlnfo("Hello World!"); } }) } } public class NoInnerClassDemo02 { public static void main(String[] args) { new X().fun1(); } }
MVC将整个程序分为三个层次:视图模型层,控制器层,与数据模型层。
特点:
将程序输入输出、数据处理,以及数据的展示分离
优势:
使程序结构变的灵活而清晰,同时也描述了程序各个对象间的通信方式,降低了程序的耦合性。
各层次:
模型层 model 主要处理数据
>数据对象封装 model.bean/domain
>数据库操作类 model.dao
>数据库 model.db
控制层
>应用界面相关 controller.activity
>存放fragment controller.fragment
>显示列表的适配器 controller.adapter
>服务相关的 controller.service
>抽取的基类 controller.base
视图层
>相关工具类 view.utils
>自定义 view.ui
对于==运算符(比较的表达式类型必须一致)
对于equals()方法
只用于引用数据类型
源自Object类,其中equals ()的定义:
public boolean equals(Object obj) {
return (this == obj);
}
说明:和 == 的作用相同,比较两个对象的地址值是否相同。
其他类自带重写:如String, Data, File, 包装类等
比较两个对象的实体内容是否相同
String类中的equals()方法重写代码:
(可用于重写Object类的equals()方法)
public boolean equals(Object obj) { if (this == anObject) { return true; } if(anObject instanceof String) { String anotherString = (String)anObject; int n = value.length; if (n == anotherString.value.length) { char v1[] = value; char v2[] = anotherString.value; int i = 0; while(n-- != 0) { if (v1[i] != v2[i]) return false; i++; } return true; } } return false; }
源自Object类
其中对toString()的定义:
public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}
String, Data, File, 包装类等都重写了Object类中toString()方法
返回实体内容信息
作用:将基本类型视为引用类型(对象)
基本类型 | 对应的引用类型 |
---|---|
boolean | java.lang.Boolean |
byte | java.lang.Byte |
short | java.lang.Short |
int | java.lang.Integer |
long | java.lang.Long |
float | java.lang.Float |
double | java.lang.Double |
char | java.lang.Char |
除java.lang.Boolean和java.lang.Char外,其余类的父类为Number
包装类,基本数据类型,String三者间的转换
基本数据类型---->包装类
调用包装类的构造器:
传入参数为代转换基本数据类型值
包装类---->基本数据类型
调用包装类的xxxValue()方法,如:
Integer in1 = new Integer(10);
int i1 = in1.intValue();
自动装箱与自动拆箱:
省去调用构造器的过程
int in1 = 10;
Integer in2 = in1;//自动装箱
Integer in1 = new Integer(10);
int in2 = in1;//自动拆箱
基本数据类型/包装类 ----> String类型
如:
int num1 = 10;
//方式1:连接运算
String str1 = num1 + "";
//方法2:调用String的valueof()方法
float f1 = 12.3f;
String str2 = String.valueof(f1);
String类型 ----> 基本数据类型、包装类
不能采用强制类型转换的方式(无子父类关系)
调用parsexxx()方法;
如:
String str = "string";
int num = Integer.parseInt(str);//等号右边返回值即为int类型
//但上述str会导致报错:NumberFormatException
关于包装类wrapper使用的面试题
Object o1 = true ? new Integer(1) : new Double(2.0);
System.out.println(o1);
思考输出结果。 1.0
解释:三元运算符会在编译时统一左右两边的数据类型,故输出结果为double
Integer m = 1;
Integer n = 1;
System.out.println(m == n);
//输出结果为true
Integer m = 128;
Integer n = 128;
System.out.println(m == n);
//输出结果为false
解释:自动装箱时会调用Integer类中的一个类叫IntegerCache,里面有个数组叫Integer cache[];默认存储 -128 到 127 int数值。
而在该范围内比较数组中的地址是缓存里同一个数组Integer cache[]
若超出范围则new新的,故地址是不同的
采取某种方法,使某个类只能有一个实例对象
饿汉式
class Demo01 {
//1.私有化类的构造器
private Demo01() {
}
//2.内部创建类的对象
//静态方法只能调用静态对象
private static Demo01 instance = new Demo();
//3.提供公共的静态的方法(方便外部获取单例对象),返回类的对象
public static Demo01 getInstance() {
return instance;
}
}
懒汉式
class Demo02 { 1.私有化类的构造器 private Demo02() { } //2.声明当前类对象(静态)(无初始化) private Demo02 instance = null; //3,声明公共的静态的返回当前类对象的方法 public static Demo02 getInstance() { if (instance == null) { //增加判断条件,保证instance严格只有一个 instance = new Demo02(); return instance; } } }
对比
饿汉式:
利:线程安全
弊:对象一开始就创建,(加载时间长)
懒汉式:
利:用的时候再创建对象
弊:目前写法,线程不安全:如,在用户A进入if内,instance还未被new的时候发生线程堵塞,用户B可以在此时也进入if内,则两者分别new了一次。
单例模式的优点:
由于单例模式只生成一个实例,减少了系统性能的开销,当一个对象的产生需要比较多的资源时,如读取配置、产生其他依赖对象时,则可以通过在应用启动时直接产生一个单例对象,然后永久驻留内存的方式来解决。
如java.lang.Runtime:
public class Runtime {
private static final Runtime currentRuntime = new Runtime();
private static Version version;
public static Runtime getRuntime() {
return currentRuntime;
}
/* Don't let anyone else instantiate this class */
private Runtime() {}
......
}
其他应用场景
概述:
规避一些非代码问题如,客户输入数据的格式,读取文件是否存在,网络是否始终保持通常等等
语法错误和逻辑错误不是异常。
分类:
常见异常,参见https://www.jianshu.com/p/a03c8807bbbc
异常处理模型:抓抛模型
过程一:“抛”,程序在正常执行过程中,一旦出现异常,就会在异常代码处生成一个对应异常类的对象。并将此对象抛出。一旦抛出对象,try内其后的代码就不再执行。
过程二:“抓”,可以理解为异常的处理方式:
try-catch-finally
try{
//可能出现的代码
}catch(异常类型1 变量名1){
//处理异常的方式1
}catch(异常类型2 变量名2){
//...
}//可多个catch
......
//可选是否使用finally
finally{
//一定会执行的代码
}
要点:
finally可选
try内代码出现异常,会生成一个对应异常类的对象,根据此对象的类型,去catch中匹配。
匹配到catch后进行异常处理,完成后寻找fianlly执行(也可能无),随后进行执行后面的代码。
catch中的异常类型若无子父类关系,则上下顺序无所谓。
若有子父类关系,要求子类一定声明在父类上面,否则会报错。
常用的异常对象处理方式:
在try结构中声明的变量,等结束try的使用后,就不能再被调用!
可以嵌套
使用try-catch-finally处理编译时异常,相当于将一个编译时可能出现的异常,延迟到运行时出现。
由于运行时异常比较常见,所以我们通常不针对运行时异常编写try-catch-finally了。针对编译时异常,我们一定要考虑异常的处理。
throws + 异常类型
写在方法声明处,指明此方法执行时,可能会抛出的异常类型。一旦方法执行时,出现异常,仍会在异常代码处生成一个异常类的对象。此对象满足throws后异常类型时,就会被抛出。异常后续的代码不再执行。
throws的方式只是将异常抛给了方法的调用者,并没有真正将异常处理掉。
真正处理掉的时try-catch-finally的方式
如何选择两种方式
手动抛出异常(throw)
区别于系统自动生成的异常类型如FileNotFoundException等。
例子
public class StudentTest { try { Student s = new Student(); s.regist(-1001); System.out.println(s); } catch (Exception e) { //e.printStackTrace(); System.out.println(e.getMessage)); } } class Student { private int id; public void regist(int id) throws Exception { if (id > 0) { this.id = id; }else{ //System.out.println("您输入的数据非法!"); //手动抛出异常: //throw new RuntimeException("您输入的数据非法!")//不用在实现类里使用try-catch,因为类型为“运行时的错误“ throw new Exception("您输入的数据非法!")//需要在实现类里加try-catch,因为Exception类型考虑了编译时出现的问题。 } } }
用户如何自定义异常
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。