1 面向对象
OOP(object oriented programming),面向对象编程是一种以对象为中心的编程思想,通过借助对象实现具体的功能将大问题拆分成小问题,然后借助不同对象分别解决,最终实现功能。
POP(procedure oriented Programming),面向过程编程是一种以过程为中心的编程思想,靠自己一步一步去实现功能,需要对每个步骤精确控制。强调按步骤实现功能,先分析解决问题所需步骤,再自定义方法实现每个步骤功能,然后依次调用方法,最终实现功能。
面向对象三大基本特征:
封装、继承、多态。而面向对象的过程就是找对象、建立对象、使用对象、维护对象的关系的过程。
1 封装
隐藏对象的属性和实现细节,仅对外提供公共访问方式,将变化隔离,便于使用,提高复用性和安全性。
2、继承
提高代码复用性;继承是多态的前提。
3、多态
父类或接口定义的引用变量可以指向子类或具体实现类的实例对象。提高了程序的拓展性。
类:是对现实生活中事物的描述。
对象:就是这类事物,实实在在存在的个体。
面向对象特点:
1、更符合人类思想习惯的思想
2、利用对象去实现功能
3、将复杂事情简单化
4、针对要解决问题的用户而言,可以把大问题拆解成小问题,分别指挥不同的
5、对象去解决小问题
6、程序员的角色由执行者变成了指挥者
对象的理解
任何事物都是一个对象(object)(万物皆对象)
对象由对象组成
每个对象都有属性(静态的描述信息)、行为(动态的功能描述)
具有相似属性和行为的对象可以归为一类
类的定义
具有相同属性和行为的对象可以抽象为类(数据类型的一种)
类的组成
属性:指事物的特征,静态描述,例如:书包的大小、品牌等
行为:指事物所具有的功能,动态描述,例如:用书包装书、从书包中取出几本书等
类的理解
- 类是对现实生活中一类具有共同属性和行为的事物的抽象
- 类是对象的数据类型,类是具有相同属性和行为的一组对象的集合
- 简单理解:类就是对现实事物的一种描述
- 类是引用数据类型中的一种。
- 类是对象的抽象,对象是类的实例
类定义格式:
[public] class 类名 {
//属性,可以包含多个
[权限修饰符] 数据类型 成员变量名;
//行为,可以包含多个
[权限修饰符] 返回值类型 成员方法名(形参列表) {
具体功能实现
}
[权限修饰符] 类名(形参列表) {
初始化语句
}
}
类的定义步骤:
- 定义类
- 编写类的成员变量
- 编写类的成员方法
案例:
class Student{
// 类 = 属性 + 行为
public long id;//学号
public String name;
public Date dob;//出生日期
public double score;//成绩
public String schoolName;//学校
// 定义(非静态方法)方法
public void learn() {
// 学生的学习行为
System.out.println("learn....");
}
}
上述案例中,我们定义了学生类Student;注意,Student是一种数据类型,是自定义类类型,属于引用类型;
类类型使用时跟int、double、String等类型类似,都必须先定义变量并赋值,才能使用;
但是,类类型和基本数据类型定义变量的方式不同,描述方式也不同,具体如下:
//基本数据类型定义变量
int a = 10; //定义一个int类型变量a
double d = 2.3; //定义一个double类型变量d
//类类型定义变量
Student stu1 = new Student(); //实例化一个Student类对象s1
Student stu2 = new Student(); //实例化一个Student类对象s2
对象的使用
创建对象格式:
类名 对象名 = new 类名();
调用成员格式:
- 对象名.成员变量;
- 对象名.成员方法 ;
案例:
public class Test01 {
int a;
static int b;
public static void main(String[] args) {
// 实例化对象
// 固定格式:类名 对象名 = new 类名();
Student stu = new Student();
stu.learn();
// 输出对象属性的默认值
// 对象属性访问格式:对象名.变量名
System.out.println(stu.name); // null
System.out.println(stu.age); // 0
// 给对象属性赋值
stu.name = "张三";
stu.age = 23;
// 输出结果:全类名@对象内存地址
// 全类名:包名.类名
System.out.println(stu);//****Student@1b6d3586
System.out.println(stu.id);//同一个地址 对应的属性值一样
}
}
class Student{
// 类 = 属性 + 行为
public long id;//学号
public String name;
public int age;
// 定义(非静态方法)方法
public void learn() {
// 学生的学习行为
System.out.println("learn....");
}
}
类的使用总结
- 一般Java程序会写两个类:基础类,测试类
- 基础类就是我们要实现封装出来的那个类
- 测试类就是包含main方法的类
- 注意:只能在一个类中定义main方法,其是程序的入口,必须唯一
对象内存
public class Test {
public static void main(String[] args) {
//实例化一个对象
Student stu = new Student();
stu.name = "tom";
stu.sayHello();
}
}
对象内存图:
程序运行过程:
- 加载Student类:把Student.class文件内容加载到方法区中
- 加载main方法并运行:整个main方法的代码都被加载到栈区中
- 创建引用类型变量:在栈空间中开辟一块内存空间,用stu标识
- 在堆中开辟内存创建对象,并给属性赋上默认初始值
- 将堆空间对象内存地址值放入stu标识的内存区域中
- 对象属性赋值:将"tom"和20放入堆空间对象内存区域内
- 对象方法调用:找到方法区sayHello方法对应的代码,执行
- main方法继续执行,遇到 } ,程序执行结束
封装的特性
概念
封装是面向对象三大特征之一,另外两个是继承,多态。
封装是指隐藏对象的属性和实现细节,仅对外提供公共访问方式。
封装的优点:
- 通过方法来控制成员变量的操作,提高了代码的安全性
- 把代码用方法进行封装,提高了代码的复用性
- 隐藏代码实现细节,提供公共访问方式,简化操作
封装的原则
- 把不需要对外提供的内容隐藏起来。
- 把属性隐藏,提供公共方法对其访问。
private
private、public等权限修饰符,都是用来修饰成员变量、成员方法和构造方法的 。
private表示私有,用它修饰类的成员(含成员变量、成员方法),则这些成员只能在类内(类的成员函数内部)去使用,其他地方不可以操作;
public表示公有,用它修饰类的成员(含成员变量、成员方法),则这些成员在
类内、类外都都可以操作。
实现封装
- 使用private修饰成员变量
- 提供对应的set和get方法,用public修饰这些方法,IDEA快捷键:Alt+Insert
- 实例化对象后,借助该对象的set方法给对象的属性赋值,get方法获取对象中的属性值。
实例:
package 自己的包名;
/**
* @author 谭梦寻
* @version 1.1
*/
class Person {
private String id;
private String name;
private String address;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
}
public class TestPerson {
public static void main(String[] args) {
//1.实例化对象,使用系统提供的无参构造器
Person person = new Person();
//2.在类外通过对象访问私有数据成员,编译报错
//person.id = "001";
//步骤3:具体使用时,借助对象的setXxx方法给属性赋值,getXxx方法获取属性值
//3.借助set方法赋值
person.setAddress("南昌");
person.setId("12423");
person.setName("小明");
System.out.println(person.toString());//等价于person
}
}
this关键字
在类中的普通成员方法中,可以使用this关键字, 其表示调用当前方法的对象引用,即哪个对象调用该方法,this就代表那个对象 。
this关键字的用法
- 对成员变量和局部变量进行区分(通常用于区分同名的局部变量和成员变量,非同名可以不使用,因为java编译器会默认调用this关键字访问成员变量)
- 固定格式: this.数据成员;
- 调用类中的成员方法
- 固定格式: this.成员方法(实际参数列表);
- 调用类中的其他构造器 ,格式:this(实际参数列表)
成员变量、局部变量、静态变量、静态方法、成员方法、构造方法的区别与联系
成员变量 :也叫全局变量,站在类的角度来说称为成员变量。它是定义在类里面,方法的外面,可以不赋予初始值,有默认的初始值。随着对象对象的存在而存在,对象的而消失而消失。
局部变量:定义在方法里面,必须初始化(赋值)后才能进行操作。随着方法的调用而存在,方法调用结束就被回收,没有默认初始值。
静态变量:又称静态属性,可以直接使用的属性。它是属于类的,为这个类的所有对象共享,只占用一块内存空间.
非静态变量:又称非静态属性,不能直接使用,必须创建了类之后才能使用,类名.属性名
静态方法:站在修饰符的角度(static),静态方法才可以直接在代码中调用 如main方法是static方法。static方法可以在没有对象实例的时候直接调用, 故可以直接调用main方法。
非静态方法:如果没有对象实例,就不能调用非静态方法。 非静态方法之间可以相互直接调用(java编译器会自动加上this)。
构造方法:(从返回值的角度)没有返回值,只有创建对象的意义,方法名和类名完全相同(区分大小写)
成员变量前加上static也是静态方法,不加static是非静态变量。区分是否是静态变量只需要看是否有修饰符static。同理,静态方法 也是如此。
构造方法
构造方法可以对对象进行初始化操作,即为对象开辟内存空间的时候,给对象的成员成员赋初值。
构造方法的格式
[修饰符] 类名(参数列表) {
初始化语句s;
}
构造方法的注意事项:
- 构造方法一般使用 public 修饰,但如果是工具类可以使用private,如String等
- 构造方法没有返回值类型
- 构造方法名和类名相同(区分大小写)
- 构造方法可以重载
- 每一个类会默认有一个无参构造方法(无参构造器),但是一旦定义了有参构造器,会覆盖掉默认的无参构造器,所以通常设置了有参构造器会另外定义一个无参构造器。
构造方法案例:
public class Person {
private String id;
private String name;
private String address;
// 每个类都默认有一个无参构造器 方法名就是类名 没有返回值 有方法体
public Person() {
// 这儿显式的给出,实际上本身就有
}
// 有参构造器 实现创建对象并赋值
// 注意定义了有参构造器 会覆盖掉默认的无参构造器
// 所以定义了有参构造器 最好重新定义一个无参构造器
// 包含三个参数的构造方法
public Person(String id, String name, String address) {
// 赋值语句
this.id = id;
this.name = name;
this.address = address;
}
// 含两个参数的构造方法
public Person(String id, String name) {
this.id = id;
this.name = name;
}
}