Трябва ли крайните полета на java клас винаги да са статични?

Не можах да намеря никакви препратки онлайн за това. Но просто исках да знам дали крайните полета в клас винаги трябва да бъдат static или това е просто конвенция. Въз основа на моето разбиране за употребата им смятам, че това е по-скоро логично нещо, отколкото нещо, което е наложено от езика.


person Karthick S    schedule 16.02.2013    source източник


Отговори (8)


Разбира се, че не. Те трябва да са статични, ако принадлежат към класа, и да не са статични, ако принадлежат към екземпляра на класа:

public class ImmutablePerson {
    private static final int MAX_LAST_NAME_LENGTH = 255; // belongs to the type
    private final String firstName; // belongs to the instance
    private final String lastName; // belongs to the instance

    public ImmutablePerson(String firstName, String lastName) {
        if (lastName.length() > MAX_LAST_NAME_LENGTH) {
            throw new IllegalArgumentException("last name too large");
        }
        this.firstName = firstName;
        this.lastName = lastName;
    }

    // getters omitted for brevity
}
person JB Nizet    schedule 16.02.2013

Не, абсолютно не - и това не е конвенция.

static и final са напълно различни неща. static означава, че полето е свързано с типа, а не с конкретен екземпляр на типа. final означава, че полето не може да промени стойността след първоначалното присвояване (което трябва да се случи по време на инициализацията на тип/екземпляр).

Полетата static final обикновено са за константи - докато полетата instance, които са final, обикновено се използват при създаване на неизменни типове.

person Jon Skeet    schedule 16.02.2013

Те не винаги се събират и това не е конвенция. Полетата final често се използват за създаване на неизменни типове:

class Person {

    private final String name;
    private final int age;

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

    public String getName() {
        return name;
    }

    public int getAge() {
        return age;
    }

}

От друга страна полетата static, но не и final не са толкова често срещани и са доста трудни. static final се вижда често, защото означава константа1за цялото приложение.

1 - добре, за целия зареждащ клас, за да бъдем точни

person Tomasz Nurkiewicz    schedule 16.02.2013

Крайните полета не необходимо да са статични и понякога може да е полезно да имате нестатична крайна променлива на екземпляр. Полетата, които са маркирани както статични, така и окончателни, обикновено се използват за константи, като това:

public static final int BORDER_WIDTH = 5;

Понякога обаче ще видите нестатично крайно поле, когато даден обект има неизменно свойство. Обикновено нестатичните final полета все още са маркирани с private поради обичайните причини, така че това е по-скоро допълнителна проверка, за да може компилаторът да се увери, че никога повече няма да задавате свойството.

person Alexis King    schedule 16.02.2013
comment
Това не е само допълнителна проверка. Финалните полета носят допълнителни гаранции за безопасност на нишките. - person JB Nizet; 16.02.2013

Ако искате да имате достъп до тях като ClassName.FIELD, тогава да, трябва да го направите. Ако не го направите статичен, трябва да направите нещо като new ClassName().FIELD, което е ненужно и безсмислено създаване на обект.

Ако обаче го използвате само в класа или го правите private, тогава не го правете статичен. Ако сте в действителния клас, можете просто да направите FIELD.

За да разберете напълно тази концепция, трябва да знаете какво означава static. Статичен означава, че принадлежи към действителния клас, а не негов екземпляр.

person tckmn    schedule 16.02.2013

Абсолютно не. Обмисли:

class Point {
    public final int x;
    public final int y;

    public Point(int _x, int _y) {
        x = _x;
        y = _y;
    }
}

Пуснете final и класът става променлив. Добавете static и всичките ви точки са еднакви и няма легален начин да напишете конструктора.

person Eric    schedule 16.02.2013

Абсолютно не. Неизменните обекти, например, имат final свойства, които могат да бъдат зададени само веднъж от конструктора.

За повече информация, моля, вижте: http://docs.oracle.com/javase/tutorial/essential/concurrency/imstrat.html

Неизменните обекти не са единственият случай, в който се използват final свойства, но те предоставят очевиден пример за тяхната полезност.

person gd1    schedule 16.02.2013

Отговорът е не.

статичен

  • #P3#
    #P4#

окончателен

  • #P6#
    #P7#
person ERROR Source Uncompilable    schedule 31.01.2018
comment
Всъщност крайните полета не са непременно постоянни. final просто означава, че препратката не може да бъде модифицирана, разгледайте например final Map<K,V> x = new HashMap<>();. Картата x е окончателна и въпреки това нейното съдържание може да се променя по време на изпълнение - така че не е константа. - person Blake; 15.03.2018