Java学习(7)—— 面向对象3(关键字)

一.   static关键字

        static可以用来修饰:属性、方法、代码块、内部类。

      (1)static修饰属性:静态变量(类变量)

               属性按是否使用static修饰可以分为:静态属性和非静态属性(实例变量)。

               实例变量:当创建了类的多个对象时,每个对象独立的拥有一套类中的非静态属性,当修改其中一个对象的非静态属性时,不会导致其他对象中同样的属性被修改。

               静态变量:当创建了类的多个对象时,多个对象共享同一个静态变量,当修改其中一个对象的静态变量时,其他对象的静态变量也被修改。

public class Test{
    public static void main(String[] args) {
        Chinese person1 = new Chinese();
        person1.name = "张";
        person1.country = "China";

        Chinese person2 = new Chinese();
        person2.name = "王";
        person2.country = "CHINA";

        System.out.println(person1.name);     //张
        System.out.println(person1.country);  //CHINA
    }
}


class Chinese{
    String name;
    int age;
    static String country;
    
}

               静态变量随着类的加载而加载,要早于对象的创建,可以通过 " 类 . 静态变量 " 的方式调用。由于类只加载一次,则静态变量在内存中也只会存在一份(在方法区的静态域中)。

public class Test{
    public static void main(String[] args) {
        Chinese.country = "中国";
        // Chinese.name = "刘";  错误:只能调用静态变量

        Chinese person1 = new Chinese();
        System.out.println(person1.country);  //中国

        Chinese person2 = new Chinese();
        System.out.println(person2.country);  //中国
    }
}


class Chinese{
    String name;
    int age;
    static String country;

}

      (2)static修饰方法:静态方法

               静态方法随着类的加载而加载,可以通过 " 类 . 静态方法 " 调用。

               在静态方法中,只能调用静态的方法或属性,在非静态方法中,既可以调用静态方法,也可以调用非静态方法。

               在静态方法中,不可以使用this和super。

public class Test{
    public static void main(String[] args) {
        Chinese.nation();
    }
}


class Chinese{
    String name;
    int age;
    static String country;

    public void show(){
        System.out.println("自我介绍");
        //调用非静态结构
        introduction();             //this.introduction();
        System.out.println(name);   //System.out.println(this.name);

        //调用静态结构
        nation();
        System.out.println(country);  //System.out.println(Chinese.country);
    }

    public static void nation(){
        System.out.println("中国人");
        //调用静态结构
        hometown();
        System.out.println(Chinese.country);

        //不能调用非静态结构
        //introduction();
        //System.out.println(name);
    }

    public void introduction(){
        System.out.println("姓名:" + name + ", 年龄:" + age);
    }

    public static void hometown(){
        System.out.println("北京");
    }
}

      属性可以被多个对象所共享,不会随着对象的不同而不同,这样的属性可以声明为statiic;

      操作静态属性的方法,通常声明为static。

二.   代码块

        代码块的作用:初始化类和对象。

        只能用static来修饰代码块,因此代码块可以分为静态代码块和非静态代码块。

        静态代码块:(1)内部可以有输出语句;(2)随着类的加载而执行,且只执行一次;(3)作用:初始化类的信息;(4)如果一个类中定义了多个静态代码块,则按声明的顺序执行;(5)静态代码块内只能调用静态的属性和方法,不能调用非静态的属性和方法。

        非静态代码块:(1)内部可以有输出语句;(2)随着对象的创建而执行,每创建一次就执行一次代码块;(3)作用:可以在创建对象时,对对象的属性等进行初始化;(4)如果一个类中定义了多个非静态代码块,则按声明的顺序执行;(5)即可以调用静态的属性和方法,也可以调用非静态的属性和方法。

public class PersonTest {
    public static void main(String[] args){
        // 静态代码块随着类的加载而执行
        String base = Person.base;     //输出: hello static
                                       //      我是一个人

        //非静态代码块随着对象的创建而执行
        Person person1 = new Person();  //输出: hello static
                                        //      我是一个人
                                        //      姓名:null, 年龄:0
        System.out.println(person1.country);  //中国
    }
}

class Person{
    //属性
    String name;
    int age;
    String country;
    static String base = "人";

    //构造器
    public Person(){

    }

    public Person(String name, int age){
        this.name = name;
        this.age = age;
    }

    //代码块
    //(1)静态代码块
    static {
        System.out.println("hello static");
        //可以调用静态属性和静态方法
        base = "我是人";
        basic();
        //不可以调用非静态属性和方法
        //country  = "中国";
        //introduction();
    }
    //(2)非静态代码块
    {
        System.out.println("hello");
        //可以调用静态属性和静态方法
        base = "我是人";
        basic();
        //可以调用非静态属性和方法
        country  = "中国";
        introduction();
    }


    //方法
    public void introduction(){
        System.out.println("姓名:" + name + ", 年龄:" + age);
    }

    public static void basic(){
        System.out.println("我是一个人");
    }
    
}

三.   final关键字

        final可以用来修饰:类、方法、变量

        final修饰类:该类不能被继承,如String类、System类

        final修饰方法:该方法不能被重写

        final修饰变量:该变量为常量,final修饰属性时可以赋值的位置有:显示初始化、代码块内初始化、构造器内初始化

public class PersonTest {
    public static void main(String[] args){

    }
}

final class Creature{     //该类不能被继承

}

//class Person extends Creature{

//}

class Person{
    String name;
    //显示初始化
    final int AGE = 22;   //该属性为常量,不能修改,必须为其赋值(赋值方式有:显示初始化、代码块内初始化、构造器内初始化)
    //AGE ++;

    final int height;
    //代码块内初始化
    {
        height = 180;
    }

    final int weight;
    //构造器内初始化
    public Person(){
        weight = 120;
    }

    public final void introduction(){     //该方法不能被重写
        System.out.println("姓名:" + name + ", 年龄:" + AGE);
    }

}


class Man extends Person{

//    public void introduction(){          不能重写
//        System.out.println("姓名:" + super.name + ", 年龄:" + super.age + "性别:" + this.sex);
//    }

}

四.   abstract(抽象类)

        abstract可以用来修饰:类、方法

        abstract修饰类:(1)抽象类不能实例化(不能创造该类的对象);(2)抽象类中可以没有抽象方法;(3)一般都会提供抽象类的子类,通过实例化子类来调用抽象类中的结构

        abstarct修饰方法:(1)抽象方法只有方法的声明,没有方法体;(2)包含抽象方法的类一定是抽象类;(3)若子类重写了父类的所有抽象方法,则可以实例化子类,如果子类没有重写父类的所有抽象方法,则需要将子类声明为抽象类。

public class PersonTest {
    public static void main(String[] args){
        //Person person = new Person();   不能创造该类的对象
        Man man = new Man();
        man.introduction();
    }
}


abstract class Person{     //抽象类
    String name;
    int age;

    public Person(){

    }

    public Person(String name, int age){
        this.name = name;
        this.age = age;
    }

    public void introduction(){
        System.out.println("姓名:" + name + ", 年龄:" + age);
    }

    abstract public void eat();    //抽象方法

}


class Man extends Person {
    char sex = '男';

    public void eat(){                 //需要对父类的抽象方法进行重写
        System.out.println("吃饭");
    }

}

五.   interface(接口)

       (1)接口和类是两个并列的结构,在接口内只能定义全局常量(public static final)、抽象方法(public abstact)、静态方法、默认方法;       

       (2)接口中不能定义构造器,因此接口不可以实例化(给接口创建对象);

       (3)接口通过类实现(implements)的方式来使用,如果实现类实现了接口中所有的方法,则此实现类可以实例化。

public class Test{
    public static void main(String[] args) {
        Boy boy = new Boy();
        boy.eat();
    }
}

interface Man{
    //全局常量
    public static final int age = 18;
    char sex = '男';   //在接口中定义的属性默认为全局常量,省略了public static final

    //抽象方法
    public abstract void eat();
    void sleep();    //在接口中定义的方法默认为抽象方法,省略了public abstract

}

class Boy implements Man{
    //实现接口中的所有方法
    public void eat(){
        System.out.println("吃饭");
    }

    public void sleep(){
        System.out.println("睡觉");
    }
}

         (4)一个类可以实现多个接口(该类需要实现所有接口中的所有方法)

                  class A extends B implements C,D :类A继承了类B,实现了接口C和D

public class Test{
    public static void main(String[] args) {

    }
}

class B{

}

interface C{

}

interface D{

}

class A extends B implements C,D{
    
}

        (5)一个接口可以继承其他接口,且可以多继承

public class Test{
    public static void main(String[] args) {

    }
}

interface A{

}

interface B{

}

interface C extends A,B{

}

        (6)接口满足多态性

public class Test{
    public static void main(String[] args) {
        Person person = new Person();
        Boy boy = new Boy();
        person.show(boy);    //吃饭
    }
}

class Person{
    public void show(Man man){     //Man man = new Boy();
        man.eat();
    }
}

interface Man{
   char sex = '男';
   void eat();
   void sleep();
}

class Boy implements Man{
    public void eat(){
        System.out.println("吃饭");
    }

    public void sleep(){
        System.out.println("睡觉");
    }
}

         (7)接口中可以定义静态方法、默认方法

public class Test{
    public static void main(String[] args) {
        Man man = new Man();

        //接口中定义的静态方法只能通过接口来调用
        //man.eat();     错误
        Person.eat();   //吃饭

        //通过实现类的对象来调用接口中的默认方法
        man.sleep();    //睡觉
        //如果实现类重写了接口中的默认方法,则调用的是重写后的方法
        man.walk();     //走路

        //如果子类(实现类)的父类和实现的接口中声明了同名同参的默认方法,并且如果子类没有对方法进行重写,则默认调用父类中的方法
        //如果实现类实现了多个接口,而这多个接口中声明了同名同参的默认方法,并且如果实现类没有对方法进行重写,则会报错;如果想要调用此方法,则必须重写
        man.live();   //生命
    }
}


interface Person{
    //静态方法
    public static void eat(){
        System.out.println("吃饭");
    }

    //默认方法
    public default void sleep(){
        System.out.println("睡觉");
    }

    public default void walk(){
        System.out.println("走");
    }

    public default void live(){
        System.out.println("活着");
    }

}

class Creature{
    public void live(){
        System.out.println("生命");
    }
}


class Man extends Creature implements Person{
    public void walk(){
        System.out.println("走路");
    }

    //在子类(实现类)中调用父类或接口中被重写的方法
    public void show(){
        walk();     //调用自己
        super.live();   //调用父类
        //调用接口
        Person.super.live();
        Person.super.walk();
    }
}

六.   内部类

        将类A声明在类B中,则类A称为内部类,类B称为外部类。

        内部类分为:成员内部类(静态、非静态)和 局部内部类(方法内、代码块内、构造器内)

        成员内部类:(1)类内可以定义属性、方法、构造器等;(2)可以被继承;(3)可以被abstract修饰;(4)可以调用外部类的结构;(5)可以被权限修饰符修饰

public class PersonTest {
    public static void main(String[] args){
        Animal.Dog dog = new Animal.Dog();   //创建静态成员内部类的实列
        dog.showDog();

        Animal animal = new Animal();
        Animal.Cat cat = animal.new Cat();   //创建非静态成员内部类的实列
        cat.eatCat();

    }
}


class Animal{
    String name;
    int age;

    public void eat(){
        System.out.println("吃饭");
    }

    static class Dog{
        int age;

        public void showDog(){
            System.out.println(age);
        }
    }

    class Cat{
        String name;
        public void showCat(){
            System.out.println(name);
        }

        public void eatCat(){
            Animal.this.eat();    //内部类内可以调用外部类的方法
        }

        public void showName(String name){
            System.out.println(name);   //形参
            System.out.println(this.name);   //Cat内的
            System.out.println(Animal.this.name);   //Animal内的
        }
    }

    public void show(){
        //局部内部类
        class A{

        }
    }

}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值