É mesmo possível?
Respostas:
se você quer dizer uma função anônima e está usando uma versão do Java anterior ao Java 8, em uma palavra, não. ( Leia sobre as expressões lambda se você usar Java 8+ )
No entanto, você pode implementar uma interface com uma função como esta:
Comparator<String> c = new Comparator<String>() {
int compare(String s, String s2) { ... }
};
e você pode usar isso com classes internas para obter uma função quase anônima :)
Aqui está um exemplo de uma classe interna anônima.
System.out.println(new Object() {
@Override public String toString() {
return "Hello world!";
}
}); // prints "Hello world!"
Isso não é muito útil como é, mas mostra como criar uma instância de uma classe interna anônima que extends Object
e @Override
seustoString()
método.
Classes internas anônimas são muito úteis quando você precisa implementar um interface
que pode não ser altamente reutilizável (e, portanto, não vale a pena refatorar para sua própria classe nomeada). Um exemplo instrutivo é usar um modelojava.util.Comparator<T>
para classificação.
Aqui está um exemplo de como você pode classificar com String[]
base em String.length()
.
import java.util.*;
//...
String[] arr = { "xxx", "cd", "ab", "z" };
Arrays.sort(arr, new Comparator<String>() {
@Override public int compare(String s1, String s2) {
return s1.length() - s2.length();
}
});
System.out.println(Arrays.toString(arr));
// prints "[z, cd, ab, xxx]"
Observe o truque de comparação por subtração usado aqui. Deve ser dito que esta técnica é quebrada em geral: ela só é aplicável quando você pode garantir que não irá estourar (como é o caso comString
comprimentos).
EventListener
(sub) implementações no aplicativo Swing médio.
Linked
barra lateral, então estou fazendo o meu melhor para fazer uso dela.
Com a introdução da expressão lambda no Java 8, agora você pode ter métodos anônimos.
Digamos que eu tenha uma aula Alpha
e desejo filtrar Alpha
s em uma condição específica. Para fazer isso, você pode usar um Predicate<Alpha>
. Esta é uma interface funcional que possui um método test
que aceita um Alpha
e retorna um boolean
.
Supondo que o método de filtro tenha esta assinatura:
List<Alpha> filter(Predicate<Alpha> filterPredicate)
Com a antiga solução de classe anônima, você precisaria de algo como:
filter(new Predicate<Alpha>() {
boolean test(Alpha alpha) {
return alpha.centauri > 1;
}
});
Com os lambdas do Java 8 você pode fazer:
filter(alpha -> alpha.centauri > 1);
Para obter informações mais detalhadas, consulte o tutorial de Expressões Lambda
Classes internas anônimas que implementam ou estendem a interface de um tipo existente foram feitas em outras respostas, embora seja importante notar que vários métodos podem ser implementados (geralmente com eventos no estilo JavaBean, por exemplo).
Um recurso pouco conhecido é que, embora as classes internas anônimas não tenham um nome, elas têm um tipo. Novos métodos podem ser adicionados à interface. Esses métodos só podem ser chamados em casos limitados. Principalmente diretamente na new
própria expressão e dentro da classe (incluindo inicializadores de instância). Isso pode confundir os iniciantes, mas pode ser "interessante" para a recursão.
private static String pretty(Node node) {
return "Node: " + new Object() {
String print(Node cur) {
return cur.isTerminal() ?
cur.name() :
("("+print(cur.left())+":"+print(cur.right())+")");
}
}.print(node);
}
(Escrevi originalmente usando, em node
vez de cur
no print
método. Diga NÃO à captura de final
locais " implicitamente "? )
node
deve ser declarado final
aqui.
cur
.
"Node" +
para tornar um segundo método necessário). / Eu não tenho nome. Talvez eu pudesse criar uma pergunta de "enquete" (CW) de nomenclatura e recebê-la no esquecimento.
Sim, se você estiver usando o java mais recente, que é a versão 8. Java8 torna possível definir funções anônimas que eram impossíveis nas versões anteriores.
Vamos dar exemplos de documentos java para saber como podemos declarar funções anônimas, classes
O exemplo a seguir, HelloWorldAnonymousClasses, usa classes anônimas nas instruções de inicialização das variáveis locais frenchGreeting e spanishGreeting, mas usa uma classe local para a inicialização da variável englishGreeting:
public class HelloWorldAnonymousClasses {
interface HelloWorld {
public void greet();
public void greetSomeone(String someone);
}
public void sayHello() {
class EnglishGreeting implements HelloWorld {
String name = "world";
public void greet() {
greetSomeone("world");
}
public void greetSomeone(String someone) {
name = someone;
System.out.println("Hello " + name);
}
}
HelloWorld englishGreeting = new EnglishGreeting();
HelloWorld frenchGreeting = new HelloWorld() {
String name = "tout le monde";
public void greet() {
greetSomeone("tout le monde");
}
public void greetSomeone(String someone) {
name = someone;
System.out.println("Salut " + name);
}
};
HelloWorld spanishGreeting = new HelloWorld() {
String name = "mundo";
public void greet() {
greetSomeone("mundo");
}
public void greetSomeone(String someone) {
name = someone;
System.out.println("Hola, " + name);
}
};
englishGreeting.greet();
frenchGreeting.greetSomeone("Fred");
spanishGreeting.greet();
}
public static void main(String... args) {
HelloWorldAnonymousClasses myApp =
new HelloWorldAnonymousClasses();
myApp.sayHello();
}
}
Sintaxe de classes anônimas
Considere a instanciação do objeto FrenchGreeting:
HelloWorld frenchGreeting = new HelloWorld() {
String name = "tout le monde";
public void greet() {
greetSomeone("tout le monde");
}
public void greetSomeone(String someone) {
name = someone;
System.out.println("Salut " + name);
}
};
A expressão de classe anônima consiste no seguinte:
new
operadoraO nome de uma interface a ser implementada ou uma classe a ser estendida. Neste exemplo, a classe anônima está implementando a interface HelloWorld.
Parênteses que contêm os argumentos para um construtor, assim como uma expressão normal de criação de instância de classe. Nota: Quando você implementa uma interface, não há construtor, então você usa um par vazio de parênteses, como neste exemplo.
Um corpo, que é um corpo de declaração de classe. Mais especificamente, no corpo, as declarações de método são permitidas, mas as instruções não.