什么是面向对象?
万物皆对象。把数据及对数据的操作方法放在一起,作为一个相互依存的整体,这个整体就是对象。
类(class)和对象
类是对对象的抽象,对象是类的具体实现。
一、构造器
class A{
private int id;
public A() {//无参构造器
}
public A(int id) {//有参构造器
this.id = id;
}
}
类默认有无参构造器。
如果手动定义了一个有参构造器,那么还要再定义一个无参构造器。
当用到单例模式时,需要将构造器私有。
单例模式:指在内存中只会创建且仅创建一次对象的设计模式。为了避免多次创建对象,且用处一样时,过多浪费资源。
二、new一个对象
栈中保存了对象的实例。相当于定义了一个类后,在栈中就存放了一个指针,用来指向堆里的对象。
堆中保存了具体的对象。
三、三大特性
1、封装
将属性私有,并给getter/setter方法
class A{
private int id;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
}
2、继承
- 关键字:
extends
- Object类是所有类的祖宗类(最“父”的那个类)
- 子类拥有父类的非private的属性和方法。
- 方法重写
this
和super
- 只能继承1个父类,可以继承多个接口。
3、多态
父类的引用指向子类的对象。
Father father = new Son();
上面这句代码产生了一个父类的实例,但是是由子类的对象(类)new出来的。这个父类的实例只能访问父类所拥有的属性和方法,而对于子类中有但父类中没有的方法是没法用的。
但是如果子类重写了父类的方法,father会调用子类的方法。举个例子:
public class Test {
public static void main(String[] args) {
Father father = new Son();
father.eat();
}
}
class Father{//父类
public void eat(){
System.out.println("eat!");
}
}
class Son extends Father{子类
public void sleep(){
System.out.println("sleep!");
}
public void eat(){//重写eat()方法
System.out.println("eat个屁!");
}
}
输出结果:eat个屁!
父类和子类可以用instanceof
关键字来匹配,从而进行类型转换。
四、修饰符
修饰符 | 简介 |
---|---|
public | 公有 |
proected | 保护 |
private | 私有 |
static | 静态 |
abstract | 抽象 |
final | 默认 |
五、接口
- 接口
interface
,只能定义方法名。 - 子类实现接口,必须重写所有的方法。
- 只有一个方法的接口叫函数式接口,可以使用lambda表达式(Java8)简化
- 函数式接口:
interface ILike{
void lambda();
}
- 实现接口
class Like implements ILike{
@Override
public void lambda() {}
}
- 在main方法中用lambda表达式实现:
like = ()->{
System.out.println("I like lambda5");
};
like.lambda();
六、内部类
1、局部内部类
访问外部类时,可以访问外部类的静态和非静态成员。就是一个很普通的类内的类。
2、静态内部类
访问外部类时,不能访问外部类的非静态成员。一般用于不需要引用外部类的地方。
类内部定义:
public static class Test{ }
相较于局部内部类,多了关键字static
3、匿名内部类
public class Test {
public static void main(String[] args) {
new A() {
@Override
public void a() {
System.out.println("aa");
}
}.a();
}
}
abstract class A{//抽象类
public void a(){};
}
定义了一个抽象类A,抽象类是不可以直接实例化的。这里利用了一个匿名内部类实现了抽象类A,再调用了它的a()方法。
匿名内部类一般用于那些一些只需要用一次的地方。