【Java】面向对象初探
前段时间经历了一段心态浮躁期,这让我想起了自己最初的计划,要提升自己知识体系的广度。前几年一直做的是web前端这一块的工作,但我希望通过自己在学习Java这样的过程来提升自己的知识广度。
面向对象概述
Java语言是一种面向对象的程序设计语言,不同于JavaScript(以下都简称为JS),它属于强类型语言。面向对象思想是一种更符合我们思考习惯的思想,它可以将复杂的事情简单化,并将我们从执行者变成了指挥者。
类与对象的关系
在JS中面向对象设计中有两个重要的概念:对象、实例,但是Java中对应的是:类、对象。及Java中的类类似于JS当中对象,Java中对象类似于JS中实例。
类是对一类事物的描述,是抽象的。对象是一类事物的实例,是具体的。类是对象的模板,对象是类的实体。
战机模板(类)
战机实物(对象)
Java类的特征及基本定义
1.类的特征
Java中的类,包含了四大基本特征,即抽象性、封装性、继承性和多态性。是属性和行为的集合。
抽象性,从上面的第一张图就可以看出来,类似于具有公共特性和行为的一张模板,不是实际的事物。封装、继承、多态性会在在后面逐一讲解。
2.类的基本定义
public class ClassName { //成员变量--->属性 //成员方法--->行为 }
3.成员变量的默认值
数据类型 |
数据类型 |
默认值 |
基本类型 |
整数(byte,short,int,long) |
0 |
浮点数(float,double) |
0.0 |
|
字符(char) |
'\u0000' |
|
布尔(boolean) |
false |
|
引用类型 |
数组,类,接口... |
null |
对象的基本使用方式
1.创建对象:
类名 对象名 = new 类名(参数列表);
2.访问成员:
对象名.成员变量;
对象名.成员方法(参数列表);
3.对象内存图
为了提高运算效率,就对空间进行了不同区域的划分,因为每一片区域都有特定的处理数据方式和内存管理方式。
JVM的内存划分:
内存区域名称 |
作用 |
寄存器 |
给CPU使用,和我们开发无关。 |
本地方法栈 |
JVM在使用操作系统功能的时候使用,和我们开发无关。 |
方法区 |
存储可以运行的class文件。存储.class相关信息,包含方法的信息。 |
堆内存 |
存储对象或者数组,new来创建的,都存储在堆内存。 堆内存中的每小块都有一个16进制的地址值。 堆内存里面的变量都有一个默认值。 |
方法栈 |
方法运行时使用的内存,比如main方法运行,进入方法栈中执行。 |
- 实例化一个对象的内存图
如上图所示,当写好的程序编译后,会把程序中对应的模块放入到对应的内存区域中。当程序执行的时候首先进入到中 main 方法(栈是先进后出,后进先出的执行方式)。遇到 Phone p ,这时候 p 保存的是 new Phone() 的地址,然后去堆内存中找对应的地址的内存小块,并执行下面的赋值操作,这时候遇到 p.sendMessage() 就会把放入到栈内存中执行(其实也是保存的是一个地址,通过这个地址去堆内存当中找到对应的代码执行相关操作)。
- 实例化多对象内存图
如果类中包含了一个方法,如果在创建多个对象的时候必然会包含这个这个方法信息,那么如果每个对象都保存一份这个方法的话必然会导致内存浪费,因此如何解决这个问题呢?请看下图:
因此对象调用方法时,根据对象中方法标记(地址值),去类中寻找方法信息。这样哪怕是多个对象,方法信息只保存一份,节约内存空间。
- 将对象作为参数传递到方法中的内存图
对象作为一种引用类型,引用类型作为参数传递的都是地址值。如果你直接输出这个p你会发现打印的事一个十六进制的数据,这个数据就是所对应的地址值。
成员变量和局部变量
类中的变量我们可以根据所定义的位置不同来区分什么是成员变量和局部变量。如下所示:
public class Person { String name; // 成员变量 public void sayHello(){ int age = 20; // 局部变量 System.out.println("我的名字"+name+"和年龄"+age) } }
成员变量和局部变量区别如下:
1.在类中的位置不同
成员变量:类中,方法外
局部变量:方法中或者方法声明上(形式参数)
2.作用范围不一样
成员变量:类中
局部变量:方法中
3.初始化值的不同
成员变量:有默认值
局部变量:没有默认值。必须先定义,赋值,最后使用
4.在内存中的位置不同
成员变量:堆内存
局部变量:栈内存
5.生命周期不同
成员变量:随着对象的创建而存在,随着对象的消失而消失
局部变量:随着方法的调用而存在,随着方法的调用完毕而消失
6.就近原则
当方法的局部变量和类的成员变量重名的时候,根据“就近原则”,优先使用局部变量。
如果需要访问本类当中的成员变量,需要使用格式:this.成员变量名。
public class Person { String name; // 成员变量 public void sayHello(String name) { // 参数name局部变量 System.out.println(name + ",你好。我是" + this.name); } }