Ссылка на анонимный внутренний класс перед его определением

В другом сообщении мне сказали что неправильно определять анонимный внутренний класс «после» (ниже) функции, которая его использует. Однако что-то вроде приведенного ниже компилируется и работает нормально:

public class CompTest {

    public static void main(String[] args) {
        TreeSet<Integer> ts = new TreeSet<Integer>(intComp);
        ts.add(1);
        ts.add(2);
        ts.add(3);
        System.out.println(ts.toString());
    }

    private static Comparator<Integer> intComp = new Comparator<Integer>() {
        @Override
        public int compare(Integer i1, Integer i2) {
            return i2.compareTo(i1);
        }
    };

}

Какое официальное слово по этому поводу? Я предполагаю, что, поскольку intComp является static, то он создается один раз, когда класс CompTest "загружается" (не знаю точно, как происходит эта загрузка, поскольку существует только основной метод и объекты CompTest не создаются), и, следовательно, когда main() нуждается в intComp, он доступен независимо от того, где в исходном файле он был фактически определен.

И даже если это работает (по вышеуказанной причине или даже по другой причине)... это плохая практика?


person The111    schedule 08.12.2012    source источник


Ответы (1)


Вы имеете в виду этот комментарий, я думаю:

"Определение компаратора должно стоять перед кодом добавления — Брайан Глейзер"

Нет технических причин помещать объявление intComp перед (или после) объявлением main. Он отлично работает в любом случае.

Единственная возможная причина, по которой компаратор ставится раньше, носит стилистический характер. То есть объявление intComp является статической переменной, и обычно объявлять переменные в начале класса.

Я склонен согласиться с пунктом стиля, но это незначительная проблема. Кроме того, если бы это был я, я бы объявил компаратор как final, дал бы ему более осмысленное имя и использовал бы «постоянный» стиль именования; например INT_COMP (но более осмысленно).


Комментарий Ре Намбари:

«Я думаю, что это плохая практика, анонимный класс предназначен для ограниченной области, а не для глобальной области».

Это нонсенс. Довольно часто анонимные классы используются таким образом. Конечно, анонимные классы также могут использоваться во вложенных областях... и это одно из их преимуществ... но это никоим образом не означает, что эта схема неверна.

person Stephen C    schedule 08.12.2012
comment
Правильно, именно этот комментарий я и имел в виду. - person The111; 08.12.2012
comment
Просто чтобы получить больше информации, почему бы вместо этого не использовать отдельный класс? Разве это не более запутанная запись? - person kosa; 08.12.2012
comment
@Nambari - 1) потому что это затрудняет чтение ... потому что теперь вам нужно искать в другом исходном файле, чтобы найти объявление ... предполагая, что это то, что вы подразумеваете под отдельным классом. 2) только если вы находите анонимные классы запутанными. И если это так, есть серьезные проблемы с вашими навыками Java. - person Stephen C; 08.12.2012
comment
@StephenC: слово «запутать» может быть неправильным, я имел в виду техническое обслуживание. - person kosa; 08.12.2012
comment
Спасибо, Стивен. Имя было просто шуткой для этого примера, я бы действительно использовал более значимое имя в реальной программе. Однако часть final я не рассматривал, и в ней тоже есть смысл. - person The111; 08.12.2012
comment
@Nambari - это тоже не помогает в обслуживании. Поверьте мне, я читаю/поддерживаю чужой Java-код уже более 10 лет. - person Stephen C; 08.12.2012