Кроме обычных методов и полей класс может иметь статические поля и методы. Например, главный класс программы имеет метод main, который является статическим:
1 2 3 |
public static void main(String[] args) { } |
Для объявления статических переменных и методов перед их объявлением указывается ключевое слово static. Статические члены класса могут использоваться без создания объектов класса.
Ранее мы уже использовали статические переменные. В частности в классе System содержится статическая переменная out
, с помощью которой выводятся данные на консоль. Например, создадим статическую переменную:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
class Book{ private int id; private static int counter=1; public void displayId(){ System.out.printf("Id: %d \n", id); } private String author; private int year; private String name; Book(String name, String author, int year){ this.name = name; this.author = author; this.year = year; id=counter++; } } |
Класс Book содержит статическую переменную counter, которая увеличивается в конструкторе и ее значение присваивается переменной id.
После этого мы можем создать несколько объектов Book, и в каждом вызове конструктора переменная counter будет увеличиваться на единицу, так как она относится не к конкретному объекту, а ко всему классу Book в целом или всем объектам Book сразу:
1 2 3 4 5 |
Book b1 = new Book("Война и мир", "Л. Н. Толстой", 1863); b1.displayId(); // выведет Id: 1 Book b2 = new Book("Отцы и дети", "И. Тургенев", 1862); b2.displayId(); // выведет Id: 2 |
Хотя в примере выше мы сразу инициализировали статическую переменную, но нередко для инициализации статических полей применяется статический блок. Этот блок вызывается один раз в программе при создании первого объекта данного класса:
1 2 3 4 5 6 7 8 9 10 11 12 |
class Book{ private int id; private static int counter; static { counter=1; System.out.println("Вызов статического блока"); } // остальной код класса } |
Нередко константы на уровне класса объявляют как статические:
1 |
public final static double PI = 3.14; |
Статические методы, подобно статическим переменным, также относятся ко всему классу. Например, создадим новый класс Algorithm и добавим в него две функции для вычисления числа Фибоначчи и факториала:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
class Algorithm{ public final static double PI = 3.14; public static int factorial(int x){ if (x == 1) { return 1; } else { return x * factorial(x - 1); } } public static int fibonachi(int x) { if (x == 0) { return 1; } if (x == 1) { return 1; } else { return fibonachi(x - 1) + fibonachi(x - 2); } } } |
Теперь используем их в программе:
1 2 3 4 |
int num1 = Algorithm.factorial(5); int num2 = Algorithm.fibonachi(5); System.out.println(Algorithm.PI); |
И поскольку методы factorial
и fibonachi
, а также поле PI
являются статическими, то мы можем к ним обратиться напрямую без создания объекта класса: Algorithm.factorial(5)
При использовании статических методов надо учитывать ограничения: в статических методах мы можем вызывать только другие статические методы и использовать только статические переменные.