目录
一、对象和类的概念
1.对象
对象用计算机语言对应问题域中事物的描述,对象通过“属性(attribute)”和“方法(method)”来分别对应事物所具有的静态属性和动态属性
2.类
类是用于描述同一类型的对象的一个抽象的概念,类中定义了这一类对象所应该具有的静态和动态属性
3.类个对象的关系
类可以堪称一类对象的模版,对象可以堪称该类的一个具体实例
1)关联关系(最弱的一种关系)
比如老师和学生和学校就属于关联关系,老师和学生有关系,学生和学校有关系
2)继承关系(一般和特殊的关系)
xx是一种xx,比如:学生是一个人,学生从人继承
3)聚合关系(整体和部分的关系)
比如男人就是人的一部分就是聚合关系
4)实现关系(与接口相关)
5)多态
二、对象和引用
1.对象
- 对象是java程序的核心,在java程序中“万事万物皆对象”
- 对象可以堪称是静态属性(成员变量)和动态属性(方法)的封装体
- 类是用来创建统一类型的对象的“模版”,在一个类中定义了该类对象所应具有的成员变量以及方法
为什么用对象:
- 面向对象的编程:一组对象相互配合通过沟通完成特定的功能
- 对象都有对外服务的接口(通过继承可以复用)
- 对象隐藏内部服务的实现(通过聚合可以复用)
对象的创建和使用:
- 必需使用new关键字创建对象
- 使用对象(引用).成员变量来引用对象的成员变量
- 使用对象(引用).方法(参数列表)来调用对象的方法
- 同一类的的每个对象有不同的成员变量存储空间
- 同一类的每个对象共享该类的方法
2.成员变量
成员变量可以使java语言中任何一种数据类型,包括基本类型和引用类型
在定义成员变量时,可以对其进行初始化,日过不初始化,java默认使用默认的值(0、null等针对不同数据类型有不同赋值,但是都是最基础的0或空)对其进行初始化(成员变量可以不初始化,局部变量必需初始化)
成员变量的作用范围为整个类体
3.引用
java语言中除基本类型之外的变量类型都称之为引用类型
java中的对象是通过引用对其进行操作的。例如:
//声明了一个string类型的引用变量,但并没有使他指向一个对象 String s; //使用new语句创建了一个string类型的对象并使用s指向它,以后可以通过s完成对其的操作 s = new String("helloWorld");
如何在内存中区分类和对象:
类是静态的概念,存放在代码区
对象是new出来的,位于堆内存,类的每个成员变量在不同的对象中都由不同的值(除静态变量)而方法只有一份,执行的时候才占用内存
三、java类的定义
//用class关键字定义一个类,例如: class person { //成员变量定义 public int id; //公有成员变量 private int age = 20; //私有成员变量 //方法定义 public int getAge() { return age; } public void setAge(int i) { age = i; } public int getId() { return id; } }
类的定义主要有两方面组成:成员变量和方法
声明类的格式为:
[modifiers] type <attr_name> [=defiultValue];
例如:public int id; private int age = 20;
声明方法的格式为:
[<modifiers>] <modifuers> <return_type> <name> ([argu_list]) {<statements>}
例如:public int getAge() {return age; }
四、构造函数(构造方法)
使用new+构造方法创建一个新的对象
构造函数是定义在java类中的一个用来初始化对象的函数
构造函数与类同名且没有返回值
例如:
//定义一个类 public class person { //定义成员变量 int id; int age; //构造方法 person(int n,int i) { id = n; age = i; } }
构造方法名与类名必需一致
构造方法不能有返回值,不能有void
创建对象时,使用构造函数初始化对象的成员变量
//定义一个测试类 public class test1 { //主方法 public static void main(String args[]) { //new了一个刚刚的person对象并传入实参 person tom = new person(1,25); person jhon = new person(2,27); } }
当没有指定构造函数时,编译器为类自动添加如:
类名(){}的构造函数,例如:
//定义一个测试类 public class test1 { public int x; //主方法 public static void main(String arg[]) { test1 x1 = new test1(); } }
如上的代码中编译是不会出现报错的,它等价于:
//定义一个测试类 public class test1 { public int x; //主方法 test1(){} //这个就是java自动生成的构造方法 public static void main(String arg[]) { test1 x1 = new test1(); } }
五、内存分析
实例一:
//定义如下类 class BirthDate { private int day; private int month; private int year; //构造方法 public BirthDate(int d,int m,int y) { day = d; month = m; year = y; } //方法1 public void setDay(int d) { day = d; } //方法2 public void setMonth(int m) { month = m; } //方法3 public int getDay() { return day; } //方法4 public int getMonth() { return month; } //方法5 public void display() { System.out.println(day + "-" + month + "-" + year); } }
//测试类 public class Test { //主方法 public static void main(String args[]) { Test test = new Test(); int date = 9; BirthDate d1 = new BirthDate(7, 7, 1970); BirthDate d2 = new BirthDate(1, 1, 2000); test.change1(date); test.change2(d1); test.change3(d2); System.out.println("date = "+date); d1.display(); d2.display(); } //定义方法 public void change1(int i) { i = 1234; } public void change2(BirthDate b) { b = new BirthDate(22, 2, 2004); } public void change3(BirthDate b) { b.setDay(22); } }
调试输出:
date = 9 7-7-1970 22-1-2000
test.change1执行完毕后date的值没有变,栈内存空间中给i分配的空间消失
test.change2执行完毕后d1的值没有变,栈内存空间中分配给b的内存空间消失,但是b指向的堆内存空间中的值暂时未消失(会由java的垃圾回收机制自动回收)
test.change3执行完毕后d2的值发生了变化,栈内存空间中分配给b的内存空间消失,d2的那个值发生变化被永远保留下来
程序执行到new一个d2对象出来的时候内存布局应该是这样的(左栈右堆):