Java 入门学习记录(五)
OOP 面向对象编程(Object Oriented Programming)
面向对象是相对于面向过程来讲的,面向对象方法,把相关的数据和方法组织为一个整体来看待,从更高的层次来进行系统建模,更贴近事物的自然运行模式,本质就是:以类的方式组织代码,以对象的组织数据
三大特性
- 封装 (Encapsulation)
- 继承 (Inheritance)
- 多态 (Polymorphism)
学到这里需要对方法
method
有一个良好的印象,加深回顾一次再继续 ! ! !区分值传递和引用传递,与内存有关
static
类与对象的创建
类是一种抽象的数据类型,它是对某一类事物整体描述,但是并不能代表一个具体的事物
对象是一个具体的实例,如:类是老师,对象为语文老师,数学老师等等,然后分别分配给他们相对应的属性和方法,相当于塑造这个对象
使用 new
关键字创建对象
Teacher teacher1 = new Teacher();
new
创建对象除了分配内存空间之外,还会给创建好的对象默认初始化,如: String
类型的初始化为 null
,以及对类中构造器( constructor )的调用
在
main
进入之前先加载类,会先执行static
代码块而构造器只有在new
之后才会调用
构造器
类中构造器也称构造方法,是在进行创建对象的时候必须调用的。并且构造器有以下两个特点:
-
必须和类的名字相同
-
必须没有返回类型,也不能写
void
在实例化对象时,会调用构造器,默认会有一个无参数的构造器,可选则显示或者不显示( 即: 手打出来 ),下面弄一个无参构造
public class Demo3 {
public static void main(String[] args) {
Demo3 demo3 = new Demo3();
System.out.println(demo3.name);
}
String name;
public Demo3(){
this.name = "Nature";
}
}
输出结果显而易见,为 Nature
有参构造在显示时,无参构造不显示无法使用,若要使用无参构造,无参构造必须显示,如上面的例子中增加几句
public Demo3(String name){
this.name = name;
}
之后在第 3 行中Demo3 demo3 = new Demo3("此处填入字符串");
则会选择有参构造的赋值方式(重载)
封装
封装就是隐藏详细的数据,通常,应禁止直接访问一个对象中的数据的实际表示,而应通过操作接口来访问,即信息隐藏
private
关键字,将属性或方法私有,不能在外操作,Java 提供了操作这个属性的方法,提供一些public
的 get
set
方法
public class Demo4 {
private String name;
private int id;
private char gender;
public static void main(String[] args) {
// 内容
}
}
get
获得数据
public String getName() {
return this.name;
}
set
给数据属性赋值
public void setName(String name) {
// 可适当增加 if 语句来提高安全性
this.name = name;
}
- 封装提高程序的安全性,保护数据
- 隐藏代码的实现细节
- 统一接口
- 提高代码的可维护性
继承
继承的本质是对某一批类的抽象,使用 extends
关键字,子类是父类的继承(扩展 )
public class <class1> extends <class2> {
}
子类(class1)拥有父类(class2)的全部方法(不可访问父类私有的属性方法),Java 只有单继承
Super
super
关键字,用来在子类中访问父类的内容,但私有的方法不可访问
this.method();
super.method();
super()
-
调用父类的构造方法,且必须在构造方法第一个
-
只能出现在子类的方法或者构造方法中
-
super() 和 this() 不能同时调用
方法重写
当子类方法需要实现功能,父类提供的方法满足不了需求时,需要重写
重写都是方法的重写,和属性无关,需要有继承关系,子类重写父类方法
方法名需要相同
参数列表相同
修饰符:范围可以扩大 到 public
抛出异常:范围,可以被缩小,但不能扩大
输出为
5 => test()
6 => test()
如图重写
输出为
5 => test()
5 => test()
当为重写时,和右边 new
的类有关系,对应;当不是重写,即子类父类方法都为 static
时,与左侧类型对应相关,即:当子类的类型为父类时,重写可以使用子类内部的方法,可以体现出子类重写了父类的方法
多态
即同一方法可以根据发送对象的不同而采用多种不同的行为方式
一个对象的实际类型是确定的,但可以指向的对象的引用类型有很多
多态的存在条件
- 有继承关系
- 子类重写父类
- 父类引用指向子类
FatherClass classname = new SonClass();
父类型,可指向子类,但是不能调用子类独有的方法
instanceof
关键字用来检验类之间的关系
static
static
方法一般称作静态方法,由于静态方法不依赖于任何对象就可以进行访问,因此对于静态方法来说,是没有 this
的,因为它不依附于任何对象,既然都没有对象,就谈不上 this
了。
并且由于这个特性,在静态方法中不能访问类的非静态成员变量和非静态成员方法,因为非`静态成员方法/变量都是必须依赖具体的对象才能够被调用。但是要注意的是,虽然在静态方法中不能访问非静态成员方法和非静态成员变量,但是在非静态成员方法中是可以访问静态成员方法/变量的。
静态代码块
static {
// 内容
}
匿名代码块
{
// 内容
}
new
之后加载顺序 静态 > 匿名 > 构造,且 static
仅仅执行一次,常用来写初始化内容
静态导入包
比如生成一个随机数,为 Math.random()
,而使用静态导包的话
import static java.lang.Math.random;
抽象类
abstract
修饰符可以用来修饰方法也可修饰类,如果修饰方法,那么该方法就是抽象方法;如果修饰类,那么该类就是抽象类
抽象类中可以没有抽象方法,但抽象方法中一定要先声明为抽象类
抽象类,不能使用 new 关键字来创建对象,它是用来让子类继承的
抽象方法,只有方法的声明,没有方法的实现,它是用来让子类实现的
子类继承抽象类,那么就必须要实现抽线类没有实现的抽象方法,否则该子类也要声明为抽象类
public abstract class Father {
public void DoMethod() {
// 内容
}
}
public class Son extends Father {
@Override
public void DoMethod() {
// 内容
}
}
接口
接口就是规范,定义一组规则
类使用 class
定义,接口使用 interface
定义,接口相当于抽象集合,内部方法相当于 public abstract
类实现接口使用 implements
关键字,实现接口的类必须重写接口中的方法
可以看到在类实现接口时,public class UserService implements Interface_1, Interface_2
这句话实现了两个接口,这说明接口是多实现的,类似于可以多继承,而继承 extends
只能单继承
接口中定义的常量为 public static final
静态常量,接口中不建议定义
接口不能被实例化,无构造方法
内部类
内部类就是在一个类的内部再定义一个类
- 成员内部类
- 静态内部类
- 局部内部类
- 匿名内部类
内部类可以访问外部类的 privat
属性
public class Outer {
private int id;
public void out() {
System.out.println("outer");
}
public class Inner {
public void in() {
System.out.println("inner");
}
public void getID() {
System.out.println(id);
}
}
}
局部内部类
public class Outer {
public void method() {
class Inner {
public void in() {
System.out.println("inner");
}
}
}
}
匿名内部类
public class hello {
public static void main(String[] args) {
new Apple().eat(); // 没有名字初始化类,不用将实例保存到变量中
}
}
class Apple {
public void eat() {
System.out.println("Eat Apple");
}
}