1. 类和对象
1.1 类和对象的理解
客观存在的事物皆为对象 ,所以我们也常常说万物皆对象。
类
类的理解
类是对现实生活中一类具有共同属性和行为的事物的抽象
类是对象的数据类型,类是具有相同属性和行为的一组对象的集合
简单理解:类就是对现实事物的一种描述
类的组成
属性:指事物的特征,例如:手机事物(品牌,价格,尺寸)
行为:指事物能执行的操作,例如:手机事物(打电话,发短信)
类和对象的关系
类:类是对现实生活中一类具有共同属性和行为的事物的抽象
对象:是能够看得到摸的着的真实存在的实体
简单理解:类是对事物的一种描述,对象则为具体存在的事物
1.2 类的定义
类的组成是由属性和行为两部分组成
属性:在类中通过成员变量来体现(类中方法外的变量)
行为:在类中通过成员方法来体现(和前面的方法相比去掉static关键字即可)
类的定义步骤:
①定义类
②编写类的成员变量
③编写类的成员方法
public class 类名 {
// 成员变量
变量1的数据类型 变量1;
变量2的数据类型 变量2;
…
// 成员方法
方法1;
方法2;
}
1.3 对象的使用
创建对象的格式:
类名 对象名 = new 类名();
调用成员的格式:
对象名.成员变量
对象名.成员方法();
示例代码
/*
创建对象
格式:类名 对象名 = new 类名();
范例:Phone p = new Phone();
使用对象
1:使用成员变量
格式:对象名.变量名
范例:p.brand
2:使用成员方法
格式:对象名.方法名()
范例:p.call()
*/
public class PhoneDemo {
public static void main(String[] args) {
//创建对象
Phone p = new Phone();
//使用成员变量
System.out.println(p.brand);
System.out.println(p.price);
p.brand = "小米";
p.price = 2999;
System.out.println(p.brand);
System.out.println(p.price);
//使用成员方法
p.call();
p.sendMessage();
}
}
1.4 学生对象-练习
需求:首先定义一个学生类,然后定义一个学生测试类,在学生测试类中通过对象完成成员变量和成员方法的使用
分析:
成员变量:姓名,年龄…
成员方法:学习,做作业…
示例代码:
public class ObjectDemo_01 {
public static void main(String[] args) {
//实例化一个对象
Student s = new Student();
//通过对象调用类中的定义的属性
s.name = "无心";
s.age = 18;
System.out.println("学生姓名:"+s.name);
System.out.println("学生年龄:"+s.age);
//通过对象调用类中的定义的成员方法
s.study();
s.doHomework();
}
}
class Student{
//定义属性
String name;
int age ;
//定义成员方法
public void study()
{
System.out.println("学到老活到老");
}
public void doHomework()
{
System.out.println("只有不断练习,才能月薪过万");
}
}
1.5Java对象在内存中的布局
以如下代码为例:
Student s = new Student();
s.name = "无心";
s.gender ="男";
s.age = 18;
class Student{
//定义属性
String name;
String gender;
int age ;
}
首先对象也是一个引用类型,第一段代码,new会在堆中创建一个空间,这个空间的大小取决于类里定义的属性,在new 的这个阶段,它会把类的信息加载Student类的信息,也就是加载属性信息和行为信息(也就方法)。
上面的示例代码中的name ,gender是String类型,我们知道String类型也是引用类型,所以在堆中存放的是有两个地址,而基本数据类型可以直接在堆中存储。
![](https://i-blog.csdnimg.cn/blog_migrate/068711debbbbe2ae788f025bec8feedd.png)
2、成员变量和局部变量
在java中,主要的变量就是属性(成员变量)和局部变量
局部变量:一般是指在成员方法中定义的变量,也就是除属性之外的其他变量,作用域为定义它的的代码块中
成员变量:我们可以称为属性或者全局变量;作用域为整个类体例如上面的student类;可以不用赋值,直接使用,因为有默认值。
局部变量必须赋值后才能使用,它没有默认值。
区别 | 成员变量 | 局部变量 |
类中位置不同 | 类中方法外 | 方法内或者方法声明上 |
内存中位置不同 | 堆内存 | 栈内存 |
生命周期不同 | 随着对象的存在而存在,随着对象的消失而消失 | 随着方法的调用而存在,随着方法的调用完毕而消失 |
初始化值不同 | 有默认的初始化值 | 没有默认的初始化值,必须先定义,赋值,才能使用 |
让我们来看看简单的代码例子:
class Cylinder{
float radius ;//成员变量radius
float height ;//成员变量height
public void bottom_Area()
{
//局部变量bottom_area
float bottom_area = 3.14f*radius*radius;
}
}
3、构造器(构造方法)
3.1构造器介绍
构造方法又叫构造器(constructor),是类的一种特殊的方法,它的主要作用是完成对新对象的初始化。它有几个特点:
方法名和类名相同
没有返回值
在创建对象时,系统会自动的调用该类的构造器完成对象的初始化
3.2基本语法
[修饰符] 方法名(形参列表){
方法体;
}
3.3为什么要用构造器
前面我们在创建学生的对象时,是先把一个对象创建好后,再给他的年龄和姓名属性赋值,如果现在我要求,在创建人类的对象时,就直接指定这个对象的年龄和姓名,该怎么做? 这时就可以使用构造器。
public class Constructor01 {
//编写一个 main 方法
public static void main(String[] args) {
//当我们 new 一个对象时,直接通过构造器指定名字和年龄
Person p1 = new Student("smith", 80);
System.out.println("p1 的信息如下");
System.out.println("p1 对象 name=" + p1.name);//smith
System.out.println("p1 对象 age=" + p1.age);//80
}
}
//在创建人类的对象时,就直接指定这个对象的年龄和姓名
class Student {
String name;
int age;
//构造器
//1. 构造器没有返回值, 也不能写 void
//2. 构造器的名称和类 Student 一样
//3. (String pName, int pAge) 是构造器形参列表,规则和成员方法一样
public Student(String pName, int pAge) {
System.out.println("构造器被调用~~ 完成对象的属性初始化");
name = pName;
age = pAge;
}
}
3.4对象创建在内存中的分析
分析如下案例:
public class ObjectDemo_02 {
public static void main(String[] args) {
Person p = new Person("一休",20)
}
}
class Person{
int age = 10;
String name ;
Person(String n, int a)
{
name = n ;
age = a ;
}
}
首先,new了一个Person,它会在堆中开辟一个新的空间,空间的大小根据Person类中的属性确定。
此时的堆中先存放的是属性中的默认值(与方法中数据类型的默认值相同)
![](https://i-blog.csdnimg.cn/blog_migrate/23e93354993b9ef8673f5d0c15f9d9a5.png)
在类中age 的值被初始化了,所以此时0被改为了10,name的值还是默认值(暂时没有被初始值)
![](https://i-blog.csdnimg.cn/blog_migrate/76f462fc5bbb220ddc7551d6f4917b25.png)
新建对象时通过构造方法将name的值初始化为了"一休",age的值初始化为20
![](https://i-blog.csdnimg.cn/blog_migrate/37467dc07ea435892320b72ec5302038.png)
![](https://i-blog.csdnimg.cn/blog_migrate/fc9ae63e7b8c4aa9775e1bb140f87aba.png)
最后在栈中让堆中对象的地址给对象p
![](https://i-blog.csdnimg.cn/blog_migrate/6e611324304548a4a2628c098aca6b5b.png)
4、this关键字
4.1this关键字的使用与介绍
this修饰的变量用于指代成员变量,其主要作用是(区分局部变量和成员变量的重名问题)
方法的形参如果与成员变量同名,不带this修饰的变量指的是形参,而不是成员变量
方法的形参没有与成员变量同名,不带this修饰的变量指的是成员变量
public class Student {
private String name;
private int age;
public void setName(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void setAge(int age) {
this.age = age;
}
public int getAge() {
return age;
}
public void show() {
System.out.println(name + "," + age);
}
}
this 的注意事项和使用细节:
this 关键字可以用来访问本类的属性、方法、构造器
this 用于区分当前类的属性和局部变量
访问成员方法的语法:this.方法名(参数列表);
访问构造器语法:this(参数列表); 注意只能在构造器中使用(即只能在构造器中访问另外一个构造器, 必须放在第一条语句)
this 不能在类定义的外部使用,只能在类定义的方法中使用
4.2this关键字在内存中的分析
分析如下代码:
public class DateTest {
public static void main(String[] args) {
MyDate birthday =new MyDate();
birthday.getname("肉松");
birthday.getDate(1999,11,05);
}
}
class MyDate{
String name ;
int year ;
int month ;
int day ;
public void getDate(int year, int month, int day)
{
this.year = year;
this.month =month;
this.day = day;
}
public void getname(String name)
{
this.name = name ;
}
在jvm内存中main 方法入栈,在main方法区先执行实例化对象。
![](https://i-blog.csdnimg.cn/blog_migrate/d64b17a01eb0426eb7b6411b0ac98d30.png)
我们可以理解为在类中都有this关键字,它是隐藏在地址中的,getname将”肉松“传出,这个是对象someone调用的方法,this指的就是这个对象。
![](https://i-blog.csdnimg.cn/blog_migrate/ed766ad9c844e8faa473cada2e845b5b.png)
3、getname方法调用完毕后,返回给main方法后出栈。继续执行getDate方法,同过this方法,在当前对象地址改变了值。
![](https://i-blog.csdnimg.cn/blog_migrate/7a22c0d57113951768ee415b496c698d.png)