Nie znalazlem nigdzie odpowiedzi.
Moga, po maksymalnie jednej klasie bazowej lub interfejsie. Powiedzialbym wrecz, ze musza:
new MouseAdapter() { ... } (klase)
new Runnable() { ... } (interfejs)
Innego sposobu na stworzenie klasy anonimowej nie znam. Nawet new Object() {} dziedziczy.
Chodzilo mi o cos takiego. Mam taki kod:
public void makeButton (String name, Color color, String key) {
ColorAction action = new ColorAction(name, color);
String iname = "panel."+name;
imap.put(KeyStroke.getKeyStroke(key), iname);
amap.put(iname, action);
panel.add(new JButton(action));
}
class ColorAction extends AbstractAction {
public ColorAction (String name, Color color) {
putValue(Action.NAME, name);
putValue(Action.SHORT_DESCRIPTION, "Zmien kolor na "+name.toLowerCase());
putValue("color", color);
}
public void actionPerformed(ActionEvent event) {
panel.setBackground((Color)getValue("color"));
}
}
No i jak widac klasa ColorAction jest potrzebna tylko w jednym miejscu, w metodzie make Button. Normalnie zmienilbym ja w klase anonimowa i wrzucil do tej metody ale ona rozszerza klase AbstractAction (definuje 6 metod interfejsu Action). Czy da sie ja jakos upchnac w tej metodzie?
Spróbuj coś takiego (pisałem to bez kompilatora, więc mogą być głupie błędy):
public void makeButton (final String name, final Color color, String key) {
AbstractAction action = new AbstractAction() {
{
putValue(Action.NAME, name);
putValue(Action.SHORT_DESCRIPTION, "Zmien kolor na "+name.toLowerCase());
putValue("color", color);
}
public void actionPerformed(ActionEvent event) {
panel.setBackground((Color)getValue("color"));
}
};
String iname = "panel."+name;
imap.put(KeyStroke.getKeyStroke(key), iname);
amap.put(iname, action);
panel.add(new JButton(action));
}
Tak jak __krzysiek85 mowi, ale mozna tez dodac przeciez domyslny konstruktor, ktory bedzie wywolany, bez zadnych cudow.
Jedna rzecz - nie lubie klas anonimowych gdy zwracam obiekt takiej klasy, ktory zyje o wiele dluzej niz obiekt klasy w ktorej jest tworzony - taki obiekt ma referencje do obiektu 'zewnetrznego', i uniemozliwia odsmiecenie go. Niby nic, ale czasami warto przemyslec sprawe. Przykladowo:
class SomeTemporaryObjectsClass {
...
public Runnable blah() {
return new Runnable() {...}
}
}
po wywolaniu metody blah() dostajesz implementacje Runnable, ktora ma referencje do obiektu SomeTemporaryObjectsClass, mimo ze moze wcale jej nie potrzebowac. Mialem juz okazje 'naprawiac' memleaki wynikajace wlasnie z takich klas anonimowych.
Ok dzieki wielkie ;) A zeby nie zakladac nowego tematu to zadam tutaj pytanie:
Dzialanie 5.3 + 2.1 zwraca mi 7.39999999999995. Dlaczego nie 7.4? Szukalem w internecie ale nic moge znalezc nic na ten temat. Dlaczego tak sie dzieje i jak to "naprawic"?
Dlatego, że nie dodałeś 5.3 + 2.1, lecz 5.3000000000000coś1 + 2.100000000000000coś2. Te "cosie" wynikają z natury reprezentacji liczb zmiennoprzecinkowych oraz koniecznej niedokładności operacji na nich (tutaj +). To jednak nie jest w ogóle problem. Użyłeś w stałych dokładności do 1 cyfry ułamkowej i w tej samej dokładności otrzymałeś wynik. Przecież 7.39999999999995 w zaokrągleniu do tej samej dokładności 1 cyfry ułamkowej ma zaokrąglenie 7.4. Czyli wynik jaki powinieneś otrzymać. Napisz sobie System.out.printf("%.1f", 5.3 + 2.1) i sam to zobaczysz. Tak więc nie musisz niczego "naprawiać".
Musisz jeszcze wiedzieć, że kompilator twoje liczby 5.3 i 2.1 zamienia na postać binarną i robi to ze skończoną dokładnością. W pamięci więc leżą nie te napisane przez Ciebie liczby, ale ich binarne przybliżenia. Na tych binarnych przybliżeniach wykonywane są operacje (też niedokładne), a na ekran wypisywana jest konwersja z binarnego wyniku na przybliżenie dziesiętne. Stąd masz właśnie taki wynik jeżeli każesz go sobie wypisać z maksymalną dokładnością.
@Olamagato - dzieki za info (tak, wiem o tym) ale zauwaz ze w watku sie rozchodzi o klasy anonimowe. Nijak ma sie klasa anonimowa do nazwanych klas zagniezdzonych, wiec komentarz hmmm z d**y ;d