#java #oop
#java #ооп
Вопрос:
У меня есть представление, в котором есть несколько кнопок «флаг» ( JToggleButton
). Когда пользователь нажимает кнопку с флажком, я хочу обновить массив, который отслеживает, какие кнопки отмечены. Это довольно просто, и вот что я сделал:
...
bflag[i].addItemListener(this); //View listens to state change
...
void itemStateChange(ItemEvent ie) {
try {
jtb = (JToggleButton)ie.getSource();
//Update mark array
}
catch (ClassCastException cce) {}
}
Это работает просто отлично, но это некрасиво с try / catch. Я бы предпочел сделать что-то вроде этого:
void itemStateChange(ItemEvent ie) {
handleStateChange(ie.getSource());
}
void handleStateChange(JToggleButton jtb) {
//handle state change
}
void handleStateChange(Object o) {}
Это намного приятнее, но единственная проблема заключается в том, что Object
метод будет срабатывать, даже если источником является JToggleButton
(потому что, в конце концов, JToggleButton
это Object
an).
Я также рассматривал возможность использования двойной отправки, но для этого потребовалось бы переопределить JToggleButton
метод, который запускает itemStateChange()
, а я не знаю, что это такое (и это кажется небезопасным).
Есть предложения о том, как заставить это работать без try / catch, условной проверки и т.д.?
Ответ №1:
Я думаю, вам нужно будет явно проверить тип.
if(ie.getSource() instanceof JToggleButton){
//toggle button logic
}else{
//something else
}
В качестве альтернативы вы можете использовать анонимные внутренние классы для реализации ваших слушателей и вообще избежать необходимости проверять источник.
Что-то вроде этого:
toggleBtn.addItemListener(new ItemListener(){
public void itemStateChange(ItemEvent ie){
//handle toggle button event
}
});
Комментарии:
1. Я думаю, что это намного уродливее, чем проверка приведения (или, по крайней мере, одинаково уродливо). Пожалуйста, подробнее остановитесь на схеме «анонимный внутренний класс».
2. @tandu Даже если оператор instanceof не улучшает красоту кода, это может быть предпочтительнее использования исключения в качестве механизма управления потоком. Я также обновил ответ примером использования анонимного внутреннего класса.
3. Анонимный внутренний класс должен был бы знать о представлении, чтобы обновить массив. Это не так.
4. Внутренний класс может обращаться к любому члену содержащего его класса. Таким образом, если массив доступен из содержащего его класса, он должен быть доступен из внутреннего класса.
5. Ах, вы правы. Но единственная проблема заключается в том, что массив необходимо обновить относительно кнопки переключения (есть несколько кнопок переключения), и анонимный класс также не может определить, какая кнопка вызвала событие!