W jaki sposób anonimowa klasa może implementować dwa (lub więcej) interfejsy? Alternatywnie, w jaki sposób może zarówno rozszerzyć klasę, jak i zaimplementować interfejs? Na przykład chcę utworzyć obiekt klasy anonimowej, który rozszerza dwa interfejsy:
// Java 10 "var" is used since I don't know how to specify its type
var lazilyInitializedFileNameSupplier = (new Supplier<String> implements AutoCloseable)() {
private String generatedFileName;
@Override
public String get() { // Generate file only once
if (generatedFileName == null) {
generatedFileName = generateFile();
}
return generatedFileName;
}
@Override
public void close() throws Exception { // Clean up
if (generatedFileName != null) {
// Delete the file if it was generated
generatedFileName = null;
}
}
};
Następnie mogę go użyć w bloku try-with-resources AutoCloseable
jako leniwie zainicjowaną klasą narzędziową:
try (lazilyInitializedFileNameSupplier) {
// Some complex logic that might or might not
// invoke the code that creates the file
if (checkIfNeedToProcessFile()) {
doSomething(lazilyInitializedFileNameSupplier.get());
}
if (checkIfStillNeedFile()) {
doSomethingElse(lazilyInitializedFileNameSupplier.get());
}
}
// By now we are sure that even if the file was generated, it doesn't exist anymore
Nie chcę, aby utworzyć klasę wewnętrzną, ponieważ jestem absolutnie pewien, że ta klasa nie zostaną wykorzystane w dowolnym miejscu z wyjątkiem metody muszę używać go w (i ja też może chcieć użyć zmienne lokalne zadeklarowane w tej metodzie, która może być var
typowym).
java
anonymous-class
izogfif
źródło
źródło
Odpowiedzi:
Klasy anonimowe muszą coś rozszerzać lub implementować, jak każda inna klasa Javy, nawet jeśli jest to zwykłe
java.lang.Object
.Na przykład:
Runnable r = new Runnable() { public void run() { ... } };
Oto
r
obiekt anonimowej klasy, która implementujeRunnable
.Klasa anonimowa może rozszerzyć inną klasę przy użyciu tej samej składni:
SomeClass x = new SomeClass() { ... };
Nie możesz zaimplementować więcej niż jednego interfejsu. Aby to zrobić, potrzebujesz nazwanej klasy. Ani anonimowa klasa wewnętrzna, ani nazwana klasa nie mogą jednak rozszerzać więcej niż jednej klasy.
źródło
SomeClass
. Ze względu na rozszerzenie domeny nadal jest anonimowe{...}
.Klasa anonimowa zazwyczaj implementuje interfejs:
new Runnable() { // implements Runnable! public void run() {} } JFrame.addWindowListener( new WindowAdapter() { // extends class } );
Jeśli masz na myśli, czy możesz zaimplementować 2 lub więcej interfejsów, to myślę, że nie jest to możliwe. Następnie możesz utworzyć prywatny interfejs, który łączy oba. Chociaż nie mogę sobie łatwo wyobrazić, dlaczego chciałbyś, aby anonimowe zajęcia miały to:
public class MyClass { private interface MyInterface extends Runnable, WindowListener { } Runnable r = new MyInterface() { // your anonymous class which implements 2 interaces } }
źródło
Klasy anonimowe zawsze rozszerzają nadklasę lub implementują interfejsy. na przykład:
button.addActionListener(new ActionListener(){ // ActionListener is an interface public void actionPerformed(ActionEvent e){ } });
Co więcej, chociaż klasa anonimowa nie może implementować wielu interfejsów, możesz utworzyć interfejs, który rozszerza inny interfejs i pozwolić swojej anonimowej klasie na jego implementację.
źródło
Chyba nikt nie zrozumiał pytania. Wydaje mi się, że ten facet chciał czegoś takiego:
return new (class implements MyInterface { @Override public void myInterfaceMethod() { /*do something*/ } });
ponieważ pozwoliłoby to na takie rzeczy, jak wiele implementacji interfejsu:
return new (class implements MyInterface, AnotherInterface { @Override public void myInterfaceMethod() { /*do something*/ } @Override public void anotherInterfaceMethod() { /*do something*/ } });
byłoby to naprawdę miłe; ale to nie jest dozwolone w Javie .
Co można zrobić, to użyć lokalnych klas wewnątrz metody bloków:
public AnotherInterface createAnotherInterface() { class LocalClass implements MyInterface, AnotherInterface { @Override public void myInterfaceMethod() { /*do something*/ } @Override public void anotherInterfaceMethod() { /*do something*/ } } return new LocalClass(); }
źródło
// The interface interface Blah { void something(); } ... // Something that expects an object implementing that interface void chewOnIt(Blah b) { b.something(); } ... // Let's provide an object of an anonymous class chewOnIt( new Blah() { @Override void something() { System.out.println("Anonymous something!"); } } );
źródło
Anonimowa klasa rozszerza się lub implementuje podczas tworzenia swojego obiektu Na przykład:
Interface in = new InterFace() { .............. }
Tutaj klasa anonimowa implementuje Interface.
Class cl = new Class(){ ................. }
tutaj Klasa anonimowa rozszerza klasę abstrakcyjną.
źródło