CodeGym/Blogue Java/Random-PT/Vamos falar sobre a palavra-chave final em Java
John Squirrels
Nível 41
San Francisco

Vamos falar sobre a palavra-chave final em Java

Publicado no grupo Random-PT
Java tem esta palavra-chave — final. Pode ser aplicado a classes, métodos, variáveis ​​(incluindo parâmetros de método). Para uma classe, a palavra-chave final significa que a classe não pode ter subclasses, ou seja, herança é proibida... Isso é útil ao criar objetos imutáveis ​​(inalteráveis). Por exemplo, a classe String é declarada como final.
public final class String {
}

class SubString extends String { // Compilation error
}
Também devo observar que o modificador final não pode ser aplicado a classes abstratas (aquelas com a palavra-chave abstract), porque esses são conceitos mutuamente exclusivos. Para um método final, o modificador significa que o método não pode ser substituído em subclasses. Isso é útil quando queremos evitar a alteração da implementação original.
public class SuperClass {
    public final void printReport() {
        System.out.println("Report");
    }
}

class SubClass extends SuperClass {
    public void printReport() { //Compilation error
        System.out.println("MyReport");
    }
}
Para variáveis ​​de tipo primitivo, a palavra-chave final significa que o valor, uma vez atribuído, não pode ser alterado. Para variáveis ​​de referência, significa que depois que um objeto é atribuído, você não pode alterar a referência a esse objeto. Isso é importante! A referência não pode ser alterada, mas o estado do objeto pode ser alterado. O Java 8 introduziu um novo conceito: efetivamente final. Aplica-se apenas a variáveis ​​(incluindo parâmetros de método). O ponto principal é que, apesar da clara ausência da palavra-chave final, o valor da variável não muda após a inicialização. Em outras palavras, a palavra-chave final pode ser aplicada a essa variável sem um erro de compilação. Variáveis ​​finais efetivamente podem ser usadas dentro de classes locais (classes internas locais), classes anônimas (classes internas anônimas) e fluxos (API Stream).
public void someMethod() {
    // In the example below, both a and b are effectively final, since they are assigned values only once:
    int a = 1;
    int b;
    if (a == 2) b = 3;
    else b = 4;
    // c is NOT effectively final since its value changes
    int c = 10;
    c++;

    Stream.of(1, 2).forEach(s-> System.out.println(s + a)); // OK
    Stream.of(1, 2).forEach(s-> System.out.println(s + c)); // Compilation error
}
Agora, vamos fazer uma pequena entrevista. Afinal, o objetivo de concluir o curso CodeGym é se tornar um desenvolvedor Java e encontrar um emprego interessante e bem remunerado. Então, vamos começar.
  1. O que podemos dizer sobre um array que é declarado final?

  2. Sabemos que a classe String é imutável: a classe é declarada final. Um valor de string é armazenado em uma matriz de caracteres marcada com a palavra-chave final.

public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence {
    /** The value is used for character storage. */
    private final char value[];
Podemos substituir o valor de um objeto String (sem alterar a referência ao objeto)? Estas são perguntas reais da entrevista. E a prática mostra que muitos candidatos não respondem corretamente. Entender como a palavra-chave final é usada, especialmente para variáveis ​​de referência, é muito importante. Enquanto você pensa nisso, farei uma pequena solicitação à equipe do CodeGym. Dê ao editor de texto a capacidade de adicionar um bloco cujo conteúdo pode ser mostrado/ocultado quando você clicar nele. Respostas:
  1. Uma matriz é um objeto, portanto, a palavra-chave final significa que, uma vez atribuída uma referência à matriz, a referência não pode ser alterada. Dito isso, você pode alterar o estado do objeto.

    final int[] array = {1, 2, 3, 4, 5};
    array[0] = 9;	 // OK, because we're changing the contents of the array: {9, 2, 3, 4, 5}
    array = new int[5]; // Compilation error
  2. Sim, nós podemos. O principal é entender o que significa a palavra-chave thorny final quando usada com objetos. A API de reflexão pode ser usada para substituir valores.

import java.lang.reflect.Field;

class B {
    public static void main(String[] args) throws Exception {
        String value = "Old value";
        System.out.println(value);

        // Get the String class's value field
        Field field = value.getClass().getDeclaredField("value");
        // Make it mutable
        field.setAccessible(true);
        // Set a new value
        field.set(value, "CodeGym".toCharArray());

        System.out.println(value);

        /* Output:
         * Old value
         * CodeGym
         */
    }
}
Observe que, se tivéssemos tentado alterar a variável final de um tipo primitivo dessa maneira, nada teria acontecido. Sugiro que você se convença: crie uma classe Java, por exemplo, com um campo int final e tente alterar seu valor usando a API Reflection. Boa sorte a todos!
Comentários
  • Populares
  • Novas
  • Antigas
Você precisa acessar para deixar um comentário
Esta página ainda não tem nenhum comentário