Java面向对象

面向对象编程 相对于面向过程编程而言
1)面向过程和面向对象的区别
将面向过程编写的代码模块化,形成多个程序组件,最终拼装运行
面向过程编程方式代码冗余较多,维护和扩展成本高,不易开发大型程序
面向对象编程:在中大型项目中,面向对象编程思维方式,能较大的改善代码冗余,提高程序的可维护性和可扩展性

面向对象的好处:
1.1)减少代码冗余,简化代码编写
1.2)提高程序的可维护性和可拓展性
2)什么是对象
Object:物品,东西(对象就是东西)
万物皆对象 对象是可操作的,用数据数值的主体
3)现实世界中是先有对象,后抽象出类型 类时概念,规定了这个类型的对象应该有的基本信息
4)java世界中先有类型,后实例化出对象(先有类型,后有对象)

5)类中包含的内容是由对象决定的
6)对象主要包含2方面的属性
6.1)属性
6.2)方法
真正使用属性和方法的是对象

String 称为字符串类型,字符串类型的值使用""引起来

7)在java中编写类
新建一个class,在class中编写这个类的属性和方法
8)新建一个包含main方法的class,对我们编写的类进行实例化
实例化后,可以通过.调用对象的属性和方法

9)使用类和对象的好处
减少代码冗余,提高程序的可维护性和可扩展性

使用java面向对象的思维处理简单问题
1)新建类(class)
类名首字母大写
新建Emp类 类中定义属性和方法 在类中直接定义的变量称为属性或成员变量
2)实例化对象
<类名> <对象名>=new <类名>();
一个类可以实例化多个对象
3)使用对象
使用对象名打.调用属性或方法
类中编写的属性和方法,最终的拥有者和使用者是对象
对象的属性有默认值(0/0.0/false/null)

一个java文件只能有一个public开头的类,而且这个类的类名必须和文件名一致
只有public开头的类中的main方法可以作为程序入口

方法重载
1)什么是方法重载(方法超载,overload)
一个类中方法签名中方法名相同,方法的参数列表不同的多个方法
方法签名:方法名+参数列表 作用:类中不允许方法签名完全相同的多个方法
方法名不同,方法签名一定不同 方法名相同,参数列表不同,也可能通过编译
2)方法重载的注意事项
方法重载的必要条件
2.1)在同一个类中(目前的学习进制中)
2.2)方法名相同
2.3)参数列表不同 参数的(个数,类型,顺序)不同 注意:变量名不同无效,比如两个方法abc(double a,int b)和abc(double x,int y)一样,不构成重载
2.4)方法重载与 访问修饰符&返回值 类型无关
3)为什么要使用方法重载
方便同一个类中功能相似的方法的记忆和调用
4)系统中的方法重载
系统中我们正在使用或使用过的有很多方法重载后的内容
4.1)System.out.println();
4.2)Arrays.copyOf();
4.3)Arrays.sort();
4.4)还有很多,数不过来
5)我们学习方法重载,在哪使用
我们今后主要将方法重载技术使用在类的构造方法中

构造方法
我们现在实例化对象后需要为对象的属性依次赋值,太麻烦,使用构造方法简化
1)什么是构造方法
就是在类进行实例化对象时运行的一个特殊的方法
构造方法也叫构造器/构造函数
2)构造方法的作用
通常情况下,使用构造方法为属性赋初值
3)构造方法的编写方式(格式)
在类中:
public <类名>() {
}
3.1)构造方法没有返回值类型(连void都不写)
3.2)构造方法方法名必须和类名相同

4)构造方法的注意事项
4.1)构造方法会在实例化对象时运行 new <类名>();
4.2)如果一个类没有编写构造方法,编译器在编译时会默认生成一个无参构造方法
4.3)如果这个类编写了构造方法,那么就不会生成默认的构造
4.4)构造方法可以重载
4.5)构造方法不能使用对象调用

局部变量和成员变量
1)局部变量时声明在 方法 中的变量
成员变量时声明在 类 中的变量(属性)
2)局部变量只能在声明它的方法中使用
成员变量能在当前类中的任何方法使用,使用范围比局部变量广
3)局部变量和成员变量重名时,局部变量具有更高的优先级
如果想输出成员变量的值,需要在变量前加 this.

this 关键字
1)this 关键字的使用
1.1)在方法中,类的属性前编写 this.
调用当前对象的属性,能够将成员变量和局部变量区分 this.<属性名>;

7.10
this 关键字
1)什么是this关键字
是对象在程序中对自身的引用
2)this的使用
2.1)this.属性
调用当前对象的属性
2.2)this.方法名()
调用当前对象的方法
2.3)this()
调用当前类构造 必须编写在当前类构造方法中的第一行

引用数据类型的数组
1)java中数据类型分两种
1.基本数据类型
2.引用数据类型
引用类型的数据保存的就是这个对象在内存中的引用
当这个引用指向同一个对象时,那么一个引用对这个对象的修改,会影响其他引用的数值

定义基本数据类型的数组
int[] nums=new int[5];

2)引用数据类型数组(String,自造类,数组)
<类型>[] 数组名=new <类型>[长度];
声明后,数组中元素的默认值为null
为数组中的元素赋值
数组名[下标]=new <类名>(<参数列表>); 如 dogs[0]=new Dog("旺财",3,5.3,"拉布拉多");
调用元素的方法
数组名[下标].属性/方法(); 如dogs[0].show();

引用数据类型声明的同时赋值
Dog[] dogs={new Dog(),new Dog(),...}

3)null和null指针
null表示当前这个引用,没有引用任何对象 所以不能对null进行任何操作
如果对null引用调用了任何属性或方法,那么就会发生NullPointerException(空指针异常)

4)多维数组(只讲二维数组)
数组的元素还是数组
声明
int[][] arr=new int[长度][]; //第一个中括号的长度必须写
arr[0]=new int[5];
arr[1]=new int[8];
...

声明的同时赋值
int[][] arr={
{5,4,14,7,5},
{45,478,4,4,5,4,1},
{1,5},
...
};

继承
面向对象编程的三(四)大特征
(抽象),封装,继承,多态
1)什么是继承
继承,是面向对象编程中一种代码复用的方式
1.1)继承财产
钱不是自己挣的,自己也能花
1.2)继承皇位
江山不是自己打的,自己也能座
1.3)继承代码
代码不是自己写的,自己也能用
2)为什么要使用继承
为了减少程序中的代码冗余,提高程序的可维护性和可扩展性
3)怎么样使用继承
格式
class <类名 A> extends <类名 B>{
}
类A继承了类B
类A中可以使用类B中的属性和方法
称类A为子类(派生类) 称类B为父类(超类/基类)
4)继承的注意事项
4.1)子类和父类应该符合is-a(是一个)关系
4.2)java中的继承是单根的
4.3)java中的继承是传递的

7.11
1.Object 类
1.1)Object类时什么
Object类是java语言中,所有类的父类
2.2)自造类和Object的关系
如果自造类不继承任何类,那它会默认继承Object

2.继承下构造方法的执行顺序
2.1)实例化子类对象时也会实例化父类对象
因为子类对象中包含着一个父类的引用
2.2)执行顺序:
先运行父类构造,再运行子类构造
2.3)默认运行
子类构造中,如果没有指定调用父类的哪一个构造
那么默认调用父类的无参构造

可以使用super关键字来指定调用父类的构造
3.super 关键字
3.1)什么是super
super是对当前对象对父类对象的引用
3.2)怎么使用super
3.2.1)super.属性
调用当前父类对象的属性
区分子类和父类的同名属性
3.2.2)super.方法名()
调用当前父类对象的方法
区分子类和父类的同名方法
3.3)super()
调用当前父类对象的构造方法
必须编写在当前类构造方法中的第一行

super只能调用父类的属性和方法,this可以调用子类也可以调用父类

构造方法中的第一行,如果不写this()或super(),默认调用super()

构造方法生成的快捷键,用Alt+/自动生成无参构造
Alt+Shift+s o 生成调用父类对象的有参构造

4.向上造型(向上转型)
1)什么是向上造型
一个子类对象,当做父类类型使用
2)为什么需要向上造型
多个不同类型的子类对象
可以使用它们的父类类型的数组来保存
3)如何使用向上造型
格式
<父类类型> <引用>=<子类对象>; Person p=new Student("王大锤",12,"男","初一");
子类对象赋给父类引用 or 父类引用指向子类对象
父类引用只能调用到父类中定义的属性和方法
4)向上造型后的问题
父类引用指向子类对象,但是这个父类的引用只能调用到父类成员

5.方法重写(方法覆盖,override)
1)什么是方法重写
子类中重新编写父类中的方法
2)为什么需要方法重写
向上造型后,父类引用不能调用到子类的成员,使用方法重写改善这个问题
当子类中对父类中某个方法的编写不满意时,就可以重写父类中的方法
3)怎么样使用方法重写
简单的方法重写
3.1)在子类中
3.2)编写一个和父类方法名相同
3.3)参数列表相同
3.4)返回值和访问修饰符也相同的方法(看下面第5点)
4)方法重写的作用
方法重写后,向上造型后的父类引用,调用子类重写后的方法时,实际运行的是子类重写后的方法
Person p=new Student("大有",22,"女","大三");
//编译时按父类类型编译
//运行时按子类对象运行
p.show();
5)方法重写的详细规则
5.1)必须相同的
1.方法名
2.参数列表
5.2)可以不同的
1.返回值类型
如果父类方法的返回值类型是void或基本数据类型,那么必须相同
如果父类方法的返回值类型是引用类型,那么子类中重写的方法的返回值可以是父类返回值类型的子类
2.访问修饰符(明天讲)
子类方法的访问修饰符不能比父类更严格
3.声明的异常(第二阶段讲)
子类重写的方法声明的异常可以是父类被重写方法声明异常的子类

方法重写和方法重载的区别
位置 方法名 参数 返回值 修饰符
重载 同类 相同 不同 无关 无关
重写 子类 相同 相同 相同* 相同* *表示不绝对,看笔记可知

*方法重载是编译期绑定,是啥类型就调用啥类型的方法
*方法重写是运行时才决定运行哪个方法,JVM会检查父类实例对象的真实类型

java程序中构造方法不能被继承,只能被调用

7.12
包(package)
1)什么是包
java程序中存放同一模块或单元
一些类的集合
2)为什么使用包
2.1)不同包中的类可以重名
2.2)方便团队开发
3)如何使用包
3.1)在类中通过包名可以访问不同包中的类
3.2)java中一个类是通过全类名来唯一标识的
全类名:包名+类名,中间用.分隔
3.3)java的包名全部小写,如果需要分隔使用.即可
3.4)如果定义一个全球范围内唯一的全类名
使用公司域名反写的方式 www.tedu.cn 反写(不写www) cn.tedu.shoot.game.Start

import 关键字
1)什么是import
java程序中,在使用不同包中的类之前,对一个类进行导入的语法格式
2)使用import导入包或类之后
再使用这个类时不需要写全类名
3)如何使用import
3.1)导入类
import java.util.Scanner;
import oopday3.pet.Cat;
3.2)导入包
import java.util.*;
import oopday3.*;
只能导入当前包中的所有类 不能导入子包中的类
3.3)导包的重名
java中不允许一个类中导入相同类名的多个类
如果一定要使用,在代码中使用全类名即可
3.4)默认的导包
java程序在编译时,会默认导入java.lang.*; 比如:String类就在java.lang.String
Math.random() 生成随机的0~1的double类型数字
java程序中默认自动导入java.lang.*;

访问修饰符
1)什么是访问修饰符
规定类中的成员的访问级别的关键字
规定了类中的属性和方法能被谁访问,不能被谁访问
2)为什么使用访问修饰符
能够增强程序的封装性,提高安全
3)认识访问修饰符
public(公有)---------->所有类
protected(保护)------->不同包的子类
默认(友好)------------>同包类
private(私有)--------->当前类

4)访问级别
所有类
不同包的子类
同包类
当前类

当前类 同包 不同包子类 其他类
public √ √ √ √ 宽松
protected √ √ √(有继承关系)
默认 √ √
private √ 严格
5)使用注意事项
5.1)类中的成员可以被4种访问修饰符修饰
5.2)非类中成员的class只能被默认或者public修饰
5.3)一般情况下,类中的属性私有,方法公有
6)属性的封装
Dog类中的属性 age 为例 age属性过大或者负值都是不合理的
为了防止不合理的赋值,提高程序运行的安全性,我们将age属性设置为私有
编写公有的方法的getters和setters为私有属性赋值或取值
在setters方法中添加条件,防止不合理赋值

final 关键字
1)什么是final关键字
final关键字也是一个修饰符,能修饰 类/方法/属性/局部变量(参数)
final是最终的意思
2)final修饰类
final class XXX{}
含义为不允许这个类被继承
原因:如果程序员要为了一个类中的某一个功能而继承这个类的话,会增加程序的架构的复杂度
3)final修饰方法
public final void xxx(){}
将一个方法修饰为final,这个类的子类中不允许重写这个方法
也可以防止无意识的重写
4)修饰成员变量(属性)
private final int a=0;
1.被final修饰的属性的属性值不允许修改
2.被final修饰的属性在对象被实例化之前必须被赋值
1.声明的同时赋值
2.构造方法中赋值
5)修饰局部变量
修饰方法中声明的局部变量,这个变量将只能被赋值一次
修饰方法的形式参数,方法里不能修改值
6)final修饰引用数据类型
这个引用的属性值可以变,但是引用(句柄)不能变化


java的工具,框架非常全面
共享的免费资料非常多
www.csdn.net

java优点:
1.java负载高
2.java安全性好
3.java速度快
4.java程序易扩展
java缺点:
1.java项目的开发周期长,导致成本高

 

7.15
1.static 关键字
1)static只能修饰类中的成员(成员变量 方法 初始化代码块)
被static修饰的称之为"静态"
没有被修饰的普通成员也被称之为"实例成员"

2)static修饰成员变量
<访问修饰符> static <类型> 变量名
private static int x;
如果一个成员变量的值需要共享给该类型的所有对象,那么就使用静态
2.1)使用静态修饰的成员变量会保存在方法区,方法区中的属性,每个类只能存一份
2.2)静态属性属于类,也叫类属性,官方建议使用类名调用
2.3)静态属性的好处是不会随实例化对象生成多份,所以节省内存空间
2.4)使用时机:当该类中的所有对象共享同一个数据或资源时

3)static修饰方法
<访问修饰符> static <返回值类型> 方法名 (<参数>) {
}
public static void abc(){}
3.1)static修饰的方法称之为静态方法,也叫类方法
3.2)静态方法可以直接使用类名调用
3.3)静态方法可以不实例化对象,直接使用
3.4)静态方法属于类,这个方法中没有也不能使用this,不能访问这个类的实例成员
3.5)静态方法不能重写
3.6)如果这个类中某个方法和当前类对象无关,就可以声明成静态的

4)static修饰初始化块
初始化代码块
在类中编写{},{}中的代码就是初始化代码块,在构造方法运行之前运行(实例化几次就运行几次)
4.1)使用static修饰初始化块,称为静态初始化代码块
无论实例化多少对象,只运行一次,而且最先运行
4.2)静态块运行时机是在JVM加载这个类时运行,所以运行时间早.又因为JVM不会重复加载一个类,所以只运行一次

2.final static 常量
public final static int WEEK=7;
(前3个修饰符位置可以调换)
1)一个成员变量同时被final和static关键字修饰,就称为常量
2)常量就是在程序中不会被修改的一个数值
3)修饰后的效果
3.1)final:不允许修改
3.2)static:使用类名调用,且只有一个
3.3)一个成员变量同时被final和static修饰,在编译时就确定值就是在运行时直接使用,提高运行效率
4)常量的命名规范
所有字母均大写,使用"_"分隔单词
5)常量一般情况下推荐声明的同时赋值,也可以在静态初始化块中赋值(但不推荐,因为效率低)

7.16
1.抽象类
1)什么是抽象类
在java程序中不存在对象的类型
2)为什么需要抽象类
抽象类能够更加直接的为程序搭建结构
3)怎么定义一个抽象类
abstract class XXX{ }
4)抽象类的特征
4.1)抽象类不能实例化
4.2)在抽象类中可以编写抽象方法
4.3)抽象方法数量不限(0~很多),可以不写抽象方法

2.抽象方法
1)什么是抽象方法
在抽象类中不能写出具体操作的方法
2)怎么定义抽象方法
在方法的返回值前加abstract
public abstract void abc();
3)抽象方法特征
3.1)抽象方法不能编写方法体
3.2)抽象方法必须在子类中被重写(除非子类也是抽象类)

3.抽象类和抽象方法
1)注意事项
1.1)abstract和final关键字不能同时修饰类和方法
1.2)不是所有父类都是抽象类
1.3)Object类不是抽象类
1.4)抽象类可以继承非抽象类
2)抽象类的意义
2.1)因为抽象类不能实例化,明确了抽象类只是程序框架,使程序结构更加清晰
2.2)抽象类除了不能实例化,拥有普通类的其他所有功能,所以特别适合作为父类提供代码复用
2.3)更自然地使用向上造型,调用子类的方法

7.17
内部类
1)什么是内部类
在一个类中,又编写了另一个类
我们将内部类称为inner 外部类称为outer
2)成员内部类
在类的成员位置,编写的内部类,称为成员内部类
2.1)成员内部类可以使用全部4种访问修饰符修饰(外部类只能是public或默认)
2.2)成员内部类中的方法可以访问外部类的私有成员
2.3)外部类可以在方法中实例化内部类对象并访问内部类的私有成员
2.4)当外部类和内部类有重名成员时: 内部类中调用外部类重名成员前加
<外部类名>.this.<外部类成员名> 如: Outer.this.n=19;
2.5)内部类要想在其他类中实例化,需要先导包到内部类,然后实例化对象
Inner inn=new Outer().new Inner();
2.6)所有内部类在编译后都会产生自己独立的class文件
3)匿名内部类
匿名内部类就是在类中通过就地实现父类(接口)而编写的一个没有名字的内部类
3.1)匿名内部类必须通过继承一个父类或实现一个接口才能编写
3.2)匿名内部类通常编写在方法中
3.3)匿名内部类也可以使用外部类的私有成员,
并且成员重名调用方法与成员内部类一样
3.4)特别需要注意:
匿名内部类的对象是向上造型后的,所以只能调用到继承的父类的可访问成员
3.5)匿名内部类的方法中是不能修改该内部类所在方法中局部变量的值
3.6)匿名内部类的方法中要获取该内部类所在方法中局部变量,需要保证局部变量只能被赋值一次(相当于有final修饰的局部变量)
3.7)JDK1.6之前(含),所有匿名内部类使用的局部变量都必须使用final修饰


2.计时器
1)什么是计时器
一般用于设定每隔一段时间调用一次某个方法的功能
2)计时器的目的
例如: 每隔1秒钟,在控制台上输出一个Hello
3)使用计时器的步骤
3.1)步骤1:
实例化一个计时器对象(导入Timer类)
3.2)步骤2:
使用匿名内部类继承TimerTask类重写方法编写每隔一段时间要做的事(导入TimerTask类)
在方法里添加timer.cancel()方法停止继续执行
3.3)步骤3:
使用计时器设置并周期性的运行TimerTask(用实例化Timer对象的.schedule()运行)

7.18
1.接口
1)什么是接口
java中的接口是一种特殊的数据类型
2)为什么需要接口
使用接口能实现java中的"多继承"(接口能间接实现java的多继承)
3)怎么定义接口
在一个java文件中
interface 接口名{
}
4)接口的特征
4.1)接口中的所有属性都是:
公有静态常量
4.2)接口中的所有方法都是:
公有抽象方法
4.3)接口中不允许有构造方法
4.4)接口不能实例化
5)编写类实现接口
5.1)在类名后通过
implements 关键字实现接口
5.2)一个类可以实现多个接口
接口名用","分隔
5.3)如果该类继承了父类,应该在父类名后编写 implements 关键字
5.4)实现接口的子类,必须重写接口中的所有方法,除非这个实现类是抽象类
6)接口类型的使用
6.1)通常情况下,接口也是向上造型的类型
Aoo a=new Child();
实现类对象赋给接口类型引用
接口类型的引用只能调用到接口中声明的方法
6.2)接口类型也可以使用匿名内部类实现
7)接口的注意事项
7.1)接口也可以继承接口
使用extends关键字
多个接口用","分隔
子接口的实现类,需要重写子接口和父接口中的所有方法
7.2)接口和实现类应该是has-a的关系
7.3)接口方法同名,有实现类引用了两个接口,不会报错
8)理解接口的含义
接口代表一种能力,实现接口的同时就代表这个类型的对象拥有了这种能力
(可以理解成一种能力的定义,实现类需要这种能力时用implements实现该接口,重写其中的公有抽象方法,即可使用该能力(方法))
9)接口的意义
9.1)使java程序间接实现了多继承
9.2)接口更加直接的设计了整个程序的结构,方便程序的拓展和维护
9.3)程序的设计人员可以通过面向接口编程减少设计工作的复杂度

7.19
1.多态
1)什么是多态
一个父类的不同子类对象对父类中声明的方法的不同调用
2)为什么使用多态
父类引用调用方法,能够运行子类重写后的方法
3)实现多态的步骤
3.1)编写父类,定义要重写的方法
3.2)子类继承父类,重写父类中的方法
3.3)子类对象赋给父类引用,父类引用调用重写后的方法
P.S. 描述中的父类可能是接口,子类可能是接口实现类

2.父类类型强制类型转换为子类类型
1)为什么需要将父类类型转换成子类类型
父类类型无法调用到子类独有的成员
2)转换格式
(子类类型)父类引用
(Dog)p; //p是Pet类型的引用
3)如何使用
3.1)转换后赋给子类引用
3.2)就地调用子类成员
3.2)强制类型转换只能发生在有继承关系的类之间

3.instanceof 关键字
1)什么是instanceof
专门用于判断一个对象是否属于一个类型的关键字
2)为什么需要instanceof
在引用类型强制类型转换之前进行判断,防止异常的发生
3)怎么使用instanceof
<引用> instanceof <类型>
运行结果是true或false,所以一般配合if使用

7.22
垃圾回收管理机制
1)什么是垃圾回收管理机制(GC)
1.1)什么是垃圾
程序中使用过的,并且之后的程序不会再使用的对象或资源
java中只有一个堆,有多个栈
1.2)什么是垃圾回收
垃圾如果放任不管,会逐渐占满内存,造成内存溢出,内存泄漏的问题
回收垃圾,就是将不使用的资源或对象释放掉的操作
1.3)垃圾回收管理机制
就是JVM自带的一个回收垃圾的线程(程序)
2)其他语言是如何回收垃圾的
C++:没有垃圾回收机制,程序员要编写代码来释放对象或资源占用的内存
通过析构函数来释放内存
3)垃圾回收机制的优点和不足:
优点:java程序员,不需要考虑垃圾回收的问题
缺点: 1.垃圾回收管理机制本身是占用内存的;
2.垃圾回收的时机并不是立即的;
3.垃圾回收管理机制,只能回收java程序中产生的垃圾.在其它的媒介中产生的垃圾要手动回收(close方法)
4)垃圾的判定和原理
4.1)判断一个对象或资源是垃圾的规则有很多
4.2)多种规则之一:引用计数法
内存中保存每个对象被引用的个数,如果这个个数为0,那么即视为垃圾
4.3)如何标记一个对象为垃圾
将引用设为null,<引用>=null;

5)finalize 方法
5.1)finalize是Object类中编写的一个方法
5.2)这个方法会被垃圾回收管理机制在回收这个对象前调用
6)System.gc();
这个方法能通知垃圾回收管理机制尽快回收程序中的垃圾

你可能感兴趣的:(Java面向对象)