0
点赞
收藏
分享

微信扫一扫

面向对象(四)

1、static关键字

1.1、如果想让一个成员变量被类的所有实例共享,就可以用static修饰,它属于类的没一个对象,称为类变量。

例如,每个中国人的国籍都属于中国,那么就不需要对每个中国人的对象都创建一个国籍的属性。

1.2、在类中的方法必须通过类实例出对象才能调用,但是有些时候我们想不创建对象也能调用类里面的方法,这种我们称为类方法,需要在类的申明时给方法加上static关键字。

1.3、static可以修饰的结构:属性、方法、代码块、内部类。

==注意:静态方法不可以调用非静态变量,但是非静态方法可以调用静态变量或者静态方法,并且在调用的时候要通过通过类来调用,不建议使用对象来调用(也不可以使用this来调用相关的静态属性或者方法,因为this要在对象被创建后才有,针对的是某个具体的类,但是静态成员变量或者方法是属于整个类的,并不属于某个具体的对象,所以不可以这样调用。)==

如下的代码所示:

Chinese类:

public class Chinese {
    private static String guoJi = "中国!";
    String name;
    int age;


    public Chinese() {
    }

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

    /**
     * 获取
     *
     * @return guoJi
     */
    public static String getGuoJi() {
        return guoJi;
    }

    /**
     * 设置
     *
     * @param guoJi
     */
    public static void setGuoJi(String guoJi) {
        Chinese.guoJi = guoJi;
    }

    /**
     * 获取
     *
     * @return name
     */
    public String getName() {
        return name;
    }

    /**
     * 设置
     *
     * @param name
     */
    public void setName(String name) {
        this.name = name;
    }

    /**
     * 获取
     *
     * @return age
     */
    public int getAge() {
        return age;
    }

    /**
     * 设置
     *
     * @param age
     */
    public void setAge(int age) {
        this.age = age;
    }

    public String toString() {
        return "Chinese{guoJi = " + guoJi + ", name = " + name + ", age = " + age + "}";
    }

    //静态方法
    public static void showInformation(){
        System.out.println("我的国籍:" + Chinese.guoJi);
    }
    
}

测试类:

public class ChineseTest {
    public static void main(String[] args) {
        Chinese chinese = new Chinese();
        chinese.showInformation();          //不建议通过这种方式调用
        //应该通过类来调用
        Chinese.showInformation();
    }

}

输出结果:

我的国籍:中国! 我的国籍:中国!

静态变量在jdk7之前,存放在方法区中,在jdk7及以后,静态变量存放在堆区中。静态变量的消亡时间为随着类的卸载而消亡。

1.4、什么时候需要使用静态变量?

①、判断当前类的多个实例是否能够共享此成员变量,且共享的成员变量的值是相同的,因为静态变量一旦修改,就会修改整个类的。

②、开发中,常将一些常量声明是静态的,比如Math类中的PI

1.5、什么时候需要使用静态方法?

①、方法内操作的变量如果是静态变量(而非实例变量)的话,则此方法建议声明为静态方法。

②、开发中,工具类中的方法都声明为静态方法。

2、单例设计模式和对main的理解

2.1、设计模式是在大量的实践中总结和理论化之后优选的代码结构,编程风格,以及解决问题的思考方式。就像是经典的棋谱,不同的棋局,我们用不同的棋谱来解局。所谓类的单例设计模式,就是采取一定的方法保证在整个的软件系统中,对某个类只能存在一个对象实例,并且该类只提供一个取得其对象的实例的方法。

2.2、实现类的单例设计模式的思路:把类的构造器权限设置为private,要获取类里面的东西,需要通过类来调用类里面的静态方法。

饿汉式单例模式:

public class Person1 {
    private static Person1 person1 = new Person1();
    private Person1(){}

    //返回对象
    public static Person1 getPerson1(){
        return person1;
    }
}

懒汉式单例模式:

public class Person2 {
    private static Person2 person2 = null;

    //获取对象
    public static Person2 getPerson2() {
        if (person2 == null) {
            person2 = new Person2();
        }
        return person2;
    }

}

两种写法的优缺点:

饿汉式:(优点)写法简单,由于在内存中较早加载,所以使用更方便,更快,是线程安全的。(缺点)内存中占用时间较长。==推荐使用这种方式。==

懒汉式:(优点)在调用时再创建,内存占用较低。(缺点)线程不安全。

2.3、main方法

2.3.1、用static修饰,表名main方法随着类的加载而加载。

2.3.2、形参的作用:与控制台交互

3、代码块(初始化块)

3.1、代码块的修饰:只能使用static进行修饰,也可以不使用。所以分为静态代码块和非静态代码块。

如下所示:

Person3类:

public class Person3 {

    public Person3() {
    }

    public String toString() {
        return "Person3{}";
    }

    //静态代码块
    static {
        System.out.println("我是静态代码块!");
    }

    //非静态代码块
    {
        System.out.println("我是非静态代码块!");
    }

    public void show() {
        System.out.println("我在吃饭!");
    }


}

测试类:

public class MyTest {
    public static void main(String[] args) {
        Person3 person3 = new Person3();
        person3.show();
    }
}

输出结果:

我是静态代码块! 我是非静态代码块! 我在吃饭!

静态代码(用于初始化类的信息)块只执行一次,而非静态代码块(用于初始化对象的信息)创建一个对象就会执行一次。静态代码块的调用方式和静态方法一样。

四、类中属性赋值的位置及过程

1、可以给类的非静态属性赋值的位置有:

①、默认初始化

②、显式初始化或代码块初始化

③、构造器中初始化

④、有了对象之后,通过方法进行对变量赋值

2、开发中如何选择上面的赋值方式?

①、当类中的属性在不同的对象中都相同的情况下,用显式初始化。

②、当类中的属性在不同的对象中不相同的情况下,用构造器初始化。

③、静态变量一般是在代码块中赋值。

五、final关键词

1、final关键字可以修饰的结构:类、方法、变量。

1.1、final修饰类,表示该类不可以被继承。

如下所示:

final public class Person {
    public void show(){
        System.out.println("我是父类");
    }
}

//下面的这种写法就是错误的,被final修饰的类不可以被继承
class Person1 extends Persson{
    
}

1.2、final修饰方法,表示该方法不能被重写。

public class Person {
    public final void show(){
        System.out.println("我是父类");
    }
}

1.3、final修饰变量,表示该变量就成为了一个常量,一旦被赋值过后就不可被修改(变量作为局部变量时,可以先声明,然后再赋值,只要在使用之前赋值就可,当作为形参的时候,不可以修改),与C++中的const相似。

1.4、那些地方可以对final成员变量赋值?

①、显式赋值

②、代码块赋值

③、构造器中赋值

1.5、final和static的混用:表示静态常量,如PI

举报

相关推荐

0 条评论