zoukankan      html  css  js  c++  java
  • Java 编程下 static 关键字

    对于每一个基于相同类所产生的对象而言,它们会拥有各自的域成员,然而在某些时候,你会想要这些对象拥有共享的域成员。举个例子来说,在 Ball 类中,打算使用到圆周率 PI 这个数据,因为对于任何一个 Ball 的实例而言,圆周率都是相同的,你不需要让不同的 Ball 实例拥有各自的圆周率域成员。

    1.静态成员变量

    可以将 PI 域成员声明为 static,被声明为 static 的域成员又称静态域成员。静态域成员是属于类所有,而不是个别的对线。可以将静态成员视为每个对象实例所共享的域成员。要声明静态域成员,只要在声明域成员时加上 static 关键字即可。例如:

    public final class Ball {
    
        public static double PI = 3.14159;
        
    }

    静态成员属于类所有,可以在不使用名称参考下,直接使用类名加上运算符来存取静态域成员,不过静态域成员同样遵守 public、protected 与 private 的存取限定。所以若要直接存取静态域成员,必须注意它的权限。例如必须设定为 public 成员,就可以通过以下语句存取:

    System.out.println("PI = " + Ball.PI);

    虽然也可以在声明对象之后,通过对象名称加上.操作符来存取静态域成员,但是这种方式并不被鼓励。通常建议使用类名加上.操作符来存取,这也可以避免于非静态域成员混淆。例如下面的方式是不被鼓励的:

    Ball ball = new Ball();
    System.out.println("PI = " + ball.PI);

    2.静态成员方法

    与静态域成员类似,也可以声明方法成员为 static 方法,又称静态方法。被声明为静态的方法通常是作为工具方法。例如在 Ball 类上增加一个角度转弧度的方法 toRadian():

    public final class Ball {
    
        public static double PI = 3.14159;
    
        public static double toRadian(double angle) {
            return PI / 180 * angle;
        }
    }

    与静态域成员一样,可以通过类名称使用.操作符来存取 static 方法,当然要注意权限设定。例如若设定为 public 可以通过以下语句存取:

    System.out.println("角度 90 等于弧度" + Ball.toRadian(90));

    静态数据与静态方法的作用通常是为了提供共享的数据或工具方法,例如将数学常用数或计算公式,以 static 声明并编写,之后可以把这个类当作工具类。通过类名称来管理与取用这些静态数据或方法,例如 J2SE 所提供的 Math 类上,就有 Math.PI 这个静态常数,以及 Math.Exp()、Math.Log()、Math.Sin() 等静态方法可以直接使用,另外 Integer.parseInt()、Integer.MAX_VALUE 等也都是静态方法与静态域成员的实际例子。

    由于静态成员是属于类而不是对象,所以当调用静态方法时,并不会传入对象的参考,即静态方法中不会有 this 参考名称。由于没有 this 名称,所以在 Java 的静态方法中不允许使用非静态成员。因为没有 this 来引用至对象,也就无法辨别要存取的是哪一个对象的成员,事实上,如果在静态方法中使用非静态域成员,在编译时就会出现以下的错误信息:

    non-static variable test cannot be referenced from a static context

    或者是在静态方法中调用非静态方法,在编译时就会出现以下的错误信息:

    non-static method showHello() cannot be referenced from a static context

    在 Java 中程序入口点(Entry Point)的 main() 方法就是静态方法,如果要直接在 main() 中调用其他的方法,则该方法就必须是静态方法。例如:

    public class Hello {
    
        public static void sayHello() {
            System.out.println("Hello World!");
        }
        
        public static void main(String[] args) {
            sayHello();
        }
        
    }

    可以试着将 sayHello() 前的 static 去掉,编译时就会发生上述的第二个错误信息。

    3.静态代码块

    Java 在使用到类时才会加载类至程序中。如果在加载类时,希望先进行一些类的初始化动作,可以使用 static 定义一个静态区块,并在当中编写类载入时的初始化动作。例如:

    public class Ball {
    
        static {
            
            // 执行初始化程序代码
            
        }
        
        // Methods
        
    }

    在类被加载时,预设会先执行静态区块中的程序代码,且只会执行一次。实际使用范例来说明一下,首先编写范例 SomeClass 类。

    public class SomeClass {
    
        static {
            
            System.out.println("类被载入");
            
        }
        
    }

    这个类只定义了静态区块,主要是为了测试类被加载时是否执行该区块,接着编写测试程序 StaticBlockDemo 类。

    public class StaticBlockDemo {
    
        public static void main(String[] args) {
    
            SomeClass someClass = new SomeClass();
    
        }
    
    }

    在使用 new 来建立 SomeClass 的实例时,SomeClass 类会被加载,加载之后预设会执行静态区块的内容,所以程序的执行结果如下:

    类被载入
    专注移动互联网产品设计研发 分享最新的移动互联网产品和技术
  • 相关阅读:
    【POJ 3162】 Walking Race (树形DP-求树上最长路径问题,+单调队列)
    【POJ 2152】 Fire (树形DP)
    【POJ 1741】 Tree (树的点分治)
    【POJ 2486】 Apple Tree (树形DP)
    【HDU 3810】 Magina (01背包,优先队列优化,并查集)
    【SGU 390】Tickets (数位DP)
    【SPOJ 2319】 BIGSEQ
    【SPOJ 1182】 SORTBIT
    【HDU 5456】 Matches Puzzle Game (数位DP)
    【HDU 3652】 B-number (数位DP)
  • 原文地址:https://www.cnblogs.com/sunzn/p/3061464.html
Copyright © 2011-2022 走看看