一、this关键字
1、this关键字总是指向调用该方法的对象
2、调用成员变量(当该方法中有个同名局部变量时)
static关键字:
static表示这个成员或者方法是属于类的,无static则是属于实例对象的。
static的成员或方法应当用类去调用,非static的用实例对象
static成员不可访问非static成员,访问一个非static成员,只能重新创建一个对象
package Capter5_ObjectOriented;
public class Dog {
public void jump(){
System.out.println("正在执行的jump方法");
}
public void run(){
this.jump();//jump()也可以
System.out.println("正在执行的run方法");
}
public static void main(String[] args){
Dog d=new Dog();
d.run();
}
}
二、方法
1、方法的参数传递
package Capter5_ObjectOriented;
public class MethodParaTransfer {
public static void swap(int a,int b){
int temp=a;
a=b;
b=temp;
System.out.println("swap方法中,a的值为:"+a+",b的值为:"+b);
}
public static void main(String[] args){
int a=6;
int b=9;
swap(a,b);
//执行过程中有两个栈区main栈区(a,b)、swap栈区(a,b),传递的只是变量的副本
//执行swap方法,改变的是副本变量的值
System.out.println("执行swap方法后,a的值为:"+a+",b的值为:"+b);
}
}
swap方法中,a的值为:9,b的值为:6
执行swap方法后,a的值为:6,b的值为:9
//引用变量的传递
package Capter5_ObjectOriented;
public class DataWrap {
int a;
int b;
}
public class MethodParaTransfer2 {
public static void swap(DataWrap dw){
int temp=dw.a;
dw.a=dw.b;
dw.b=temp;
System.out.println("swap方法中,成员变量a的值为:"+dw.a+",成员变量b的值为:"+dw.b);
}
public static void swap1(DataWrap dw){
int temp=dw.a;
dw.a=dw.b;
dw.b=temp;
dw=null;
System.out.println("这个对象的dw只是一个副本,一旦为null,main中的dw不收影响");
}
public static void main(String[] args){
DataWrap dw=new DataWrap();
swap(dw);
System.out.println("执行swap方法后,成员变量a的值为:"+dw.a+",成员变量b的值为:"+dw.b);
//方法的传递都是值传递,或者说引用的值传递,这两个dw是不一样的,但是DataWrap()这个堆中的无法复制,因此这两个同名的引用变量指向同一个对象
//因为指向一致,因此对指向的修改是共享的。
//但这两个变量是不同的,如下例
swap1(dw);
System.out.println("执行swap方法后,成员变量a的值为:"+dw.a+",成员变量b的值为:"+dw.b);
}
}
2、形参个数可变的方法
package Capter5_ObjectOriented;
public class Var_args {
public static void test(int a,String...books){
for(String book:books){
System.out.println(book);
}
System.out.println(a);
}
public static void main(String[] args){
test(3,"疯狂java讲义","轻量级java EE企业应用实战");
}
}
三、成员变量与局部变量
成员变量:类变量(static修饰),实例共享
实例变量(不用static修饰),实例独有
局部变量:形参、方法局部变量、代码块局部变量
注意:如果通过一个实例修改一个类变量的值,其它实例的该类变量也将共享
这个修改之后的值。
1、成员变量在系统加载类或者创建类的实例的时候,系统自动为成员变量分配内存空间,并且指定初始值
2、局部变量必须经过显式初始化才会分配内存。随方法或者代码块的结束而结束。
四、隐藏与封装
1、封装
封装:隐藏类的实现细节、限制对成员变量的不合理访问、便于数据检查及维护
getter与setter
五、深入构造器
package Capter5_ObjectOriented;
public class constructor {
public String name;
public int age;
public double weight;
constructor(){}
constructor(String name,int age){
this.name=name;
this.age=age;
}
constructor(String name,int age,double weight){
this(name,age);
this.weight=weight;
}
}
六、类的继承
1、父类中的方法或成员变量被子类的覆盖时,可使用super.变量、super.方法
2、子类可调用父类的构造器,如super(name,age)
3、不允许多重继承,但会有很多间接继承
七、多态
java引用变量的两种类型:编译时的类型(由声明该变量时的类型决定)
运行时的类型,由赋给该变量的对象决定
如果编译时的类型与运行时的类型不一致就可能出现所谓的多态
package Capter5_ObjectOriented;
public class BaseClass {
public int book;
public void base(){
System.out.println("父类的普通方法");
}
public void test(){
System.out.println("父类被覆盖的方法");
}
}
public class Subclass extends BaseClass{
public String book="java讲义";
public void test(){
System.out.println("子类覆盖父类的方法");
}
public void sub(){
System.out.println("子类的普通方法");
}
public static void main(String[] args){
BaseClass b = new Subclass();
/*
* java允许一个子类对象赋给一个父类引用变量,为多态产生的条件
* 通过引用变量访问其包含的实例变量时,总是试图访问它编译时类型所定义的实例变量
* BaseClass为b编译时的类型,Subclass为运行时的类型,因此test为子类的方法
* 注意:不允许编译BaseClass没有的方法,编译不会通过,如b.sub()
*/
System.out.println(b.book);//父类的实例变量
b.test();//子类的方法
b.base();//父类的方法,因为子类没有覆盖
Subclass s = (Subclass) b;//强制转换,因为b的实际运行类型为Subclass
System.out.println(s.book);//可调用子类的实例变量
s.sub();//可调用子类的独有方法
if(b instanceof BaseClass){
System.out.println("判断前一个对象是否后面的类、其子类、实现类的实例");
}
}
}
八、继承与组合
继承破坏父类的封装性(子类可随意访问及修改),设计父类时有几个注意点:
1、尽可能将父类成员变量设置为private
2、辅助其它工具的方法设置为private;需要给外部调用public+final;希望被子类重写,但不想被其它类自由访问protected
3、尽量不要在父类构造器中调用要被子类重写的方法
要复用一个类,除了继承还有组合。
继承一般是is-a的关系,组合想要表达的是has-a(整体与部分)的关系
package Capter5_ObjectOriented;
public class Animal {
private void beat(){
System.out.println("心脏跳动……");
}
public void breath(){
beat();
System.out.println("呼吸中");
}
}
public class Bird {
private Animal a;
public Bird(){}
public Bird(Animal a){
this.a=a;
}
public void breath(){
a.breath();//对breath的复用
}
}
’