类:自定义类型(定义一个新的数据类型),实体的抽象 一般用class(包括数据成员,方法)
对象:真正存在的一个实体 用关键字new(实例化一个对象,在堆上)
类是对象的一个模板,而对象就是类的一个实例,在类中,数据或变量被称为实例变量,代码包含在方法内,定义在类中的方法和实例变量被称为类的成员,在大多数类中,实例变量被定义在该类中的方法中操作或存取。
一个简单的类
class Box{
double chang;
double kuan;
double gao;
}
记住类声明只是创建了一个模板,要真正创建一个Box对象,必须使用下面语句
Box mybox=new Box();
每次创建类的一个实例时,是在创建一个对象,该对象包含他自己的由类定义的每个实例变量的拷贝,因此,上面例子中的每个Box对象都包括他自己的实例变量拷贝,这些变量即chang,kuan,gao,要访问这些变量,必须使用“.”运算符。例如,要将chang赋值10,用下面的语句:
mybox.chang=10;
下面是Box类的完整程序:
package study;
//类和对象
class Box{
double chang;
double kuan;
double gao;
}
class BoxDemo{//应该把文件名命名为BoxDemo.java,因为main方法在BoxDemo类中,而不是Boxde的类中
public static void main(String[] args) {
Box mybox=new Box();
double tiji;
mybox.chang=10;
mybox.kuan=8;
mybox.gao=7;
tiji=mybox.chang*mybox.kuan*mybox.gao;
System.out.println("体积为:"+体积ji);
}
}
声明对象
获得一个类的对象需要两步,第一步,必须声明该类类型的一个变量,这个变量没有定义一个对象,实际上,它只是一个能够引用对象的简单变量,第二步,该声明要创建一个对象的实际的物理拷贝,并把该对象的引用赋给该变量,这是通过new运算符来实现的,new运算符为对象动态(即在运行时分配)分配内存空间,并返回它的一个引用,这个引用或多或少是new分配给对象的内存地址,然后这个引用储存在该变量中。同样用上面的例子,用下面的语句来声明一个Box类型的对象:
Box mybox=new Box();
可以改写成下面的形式:
Box mybox;//声明了mybox,把它作为对于Box类型的对象的一个引用,当本句执行时,mybox包含的值为null,表示它没有引用对象,
mybox=new Box();//创建一个实际的对象,并把对于它的引用赋给mybox
new运算符
new运算符动态的为一个对象分配地址,它的通用格式如下:
所创建类类型的变量=new 被实例化类的名字();
mybox=new Box();
之所以对整数或字符这样的简单变量不使用new运算符,是因为java的简单类型不是作为对象实现的,出于效率的考虑,它们是作为常规变量实现的。类的后面跟的圆括号指定了类的构造函数,即调用了该类的构造函数,构造函数定义当创建一个类的对象时将发生什么,构造函数是所有类的重要组成部分,并有许多重要的属性。大多数类在他们自己的内部显式的定义构造函数,如果一个类没有显示的定义自己的构造函数,那么java将自动的提供一个默认的构造函数。
构造函数
构造函数的任务就是初始化一个对象的内部状态,以便使创建的实例变量能够完全初始化,可以被对象马上使用,构造函数必须满足以下三个条件:
1.方法名必须与类名相同;
2.在方法名前没有返回值类型的声明;
3.在方法中不能使用return返回一个值
package study;
class Box{
double chang;
double kuan;
double gao;
Box(){//构造函数,如果不写这个java自己也会提供一个构造函数,并参与运行,但java自己提供的你看不到,并且它自己生成的构造函数默认值都为0(即此例中默认构造函数的chang=kuan=gao=0),(对于boolean默认为false,char默认\u0000)
System.out.println("进入默认构造函数");//加println为了说明的缘故,绝大多数构造函数功能不显示任何东西,它们仅简单的初始化一个对象
chang=10;
kuan=8;
gao=7;
}
double tiji(){
return chang*kuan*gao;
}
}
public class BoxDemo1 {
public static void main(String[] args) {
Box mybox1=new Box();
Box mybox2=new Box();
double tj;
tj=mybox1.mianji();
System.out.println("体积为:"+tj);
体j=mybox2.mianji();
System.out.println("体积为:"+tj);
}
}
带自变量的构造函数
前面的例子不够实用,因为不是所有的盒子都是一个尺寸,我们可以定义一个自变量构造函数,它根据自变量设置每个指定盒子的尺寸,
package study;
class Box{
double chang;
double kuan;
double gao;
Box(double c,double k,double g){
chang=c;
kuan=k;
gao=g;
}
double tiji(){
return chang*kuan*gao;
}
}
class BoxDemo2 {
public static void main(String[] args) {
Box mybox1=new Box(10,8,6);
Box mybox2=new Box(5,2,1);
double tj;
tj=mybox1.mianji();
System.out.println("体积为:"+tj);
tj=mybox2.mianji();
System.out.println("体积为:"+tj);
}
}
this关键字
有时一个方法需要引用调用它的对象,为此,java定义了this这个关键字,this可以在引用当前对象的所有方法内使用(在无参构造方法中可以使用this关键字调用有参的构造方法,但使用这种方式需要注意的是,只可以在无参数构造方法的第一句使用this调用有参数的构造方法),也就是,this总是调用该方法的一个引用,所以你可以在当前类的类型所允许对象的任何一个地方将this作为一个引用
Box(double c,double k,double g){
this.chang=c;
this.kuan=k;
this.gao=g;
}
当然在本例中this是冗余的,但是完全正确,我们来看另外一个例子,定义一个雇员类(员工号、姓名、薪水、部门),在这个类中提供四个工作方法:
A、单参,只传递员工号,则员工姓名:无名氏,薪水:0,部门:未定
B、双参,传递员工号,姓名,则员工薪水为1000,部门:后勤
C、四参,传递员工号,姓名,部门,薪水
D、无参,则均为空值
来看代码:
package study;
class Emp {
private int xinming ;
private String xinshi ;
private double gonzi ;
private String bumen ;
public Emp(){}
public Emp(int empno){
this.xinming = xinming ;
this.xinshi = "无名氏" ;
this.gonzi = 0.0 ;
this.bumen = "未定" ;
}
public Emp(int empno,String ename){
this.xinming = xinming ;
this.xinshi = xinshi ;
this.gonzi = 1000.0 ;
this.bumen = "后勤" ;
}
public Emp(int empno,String ename,double salary,String dept){
this.xinming = xinming ;
this.xinshi = xinshi ;
this.gonzi = gonzi ;
this.bumen = bumen ;
}
public String getInfo() {
return "雇员编号:" + this.xinming + ",姓名:" + this.xinshi + ",工资:" + this.gonzi + ",部门:" + this.bumen ;
}
}
public class TestDemo3{
public static void main(String args[]) {
Emp emp1 = new Emp();
System.out.println(emp1.getInfo());
Emp emp2 = new Emp(4555);
System.out.println(emp2.getInfo());
Emp emp3 = new Emp(6542,"小王");
System.out.println(emp3.getInfo());
Emp emp4 = new Emp(4578,"小明",12000,"技术部");
System.out.println(emp4.getInfo());
}
}
垃圾回收
当一个对象的引用不存在时,则该对象会被认为是不在需要的,它所占用的内存就会被释放掉。
public class StringDemo {
public static void main(String args[]) {
String str = "Hello " ;
str += "World " ;
str = str + "!!!" ;
System.out.println(str) ;
}
}
运行结果:
Hello World !!!
内存分配如图:
1,2最终会成为垃圾被回收