Qual é o estilo aceito para usar a palavra-chave `this` em Java?

37

Eu venho de linguagens como Python ou Javascript (e outras menos orientadas a objetos) e estou tentando melhorar meu conhecimento prático de Java, que eu conheço apenas superficialmente.

É uma prática ruim sempre preceder thisos atributos da instância atual? Parece mais natural para mim escrever

...
private String foo;

public void printFoo() {
    System.out.println(this.foo);
}
...

do que

...
private String foo;

public void printFoo() {
    System.out.println(foo);
}
...

pois me ajuda a distinguir atributos de instância de variáveis ​​locais.

Obviamente, em uma linguagem como Javascript, faz mais sentido usar sempre this, pois é possível ter mais aninhamento de funções, portanto variáveis ​​locais provenientes de escopos maiores. Em Java, até onde eu entendo, nenhum aninhamento como esse é possível (exceto para classes internas), portanto, provavelmente não é um grande problema.

Em qualquer caso, eu preferiria usar this. Seria estranho e não idiomático?

Andrea
fonte
Usamos uma ferramenta para padronizar isso em nossa empresa. A ferramenta reencaminha o código com o nosso sem isso, dependendo da política da empresa. Então, todo mundo codifica como eles gostam e o código é formatado da maneira certa no momento da confirmação.
deadalnix
2
"desde que se possa ter mais aninhamento de funções, portanto variáveis ​​locais provenientes de escopos maiores." Além disso, o fato de que "this" não é realmente um dos lugares em que uma variável não qualificada pode surgir em uma função em JS.
Random832
2
Prefixo todas as variáveis ​​de instância com sublinhado para que eu possa distinguir facilmente a diferença entre variáveis ​​locais e de instância sem usar this.
WuHoUnited
4
No C #, StyleCop quer que você coloque this.quando se refere a variáveis-membro, métodos, etc. Gosto disso, concordo com esta regra. Eu acho que é melhor do que nomear algo com um sublinhado no começo. Eu seguiria a mesma regra se estivesse codificando em java.
Job

Respostas:

40

Na maioria dos IDEs, você pode simplesmente passar o mouse sobre a variável, se quiser saber. Além disso, realmente, se você estiver trabalhando em um método de instância, deve realmente conhecer todas as variáveis ​​envolvidas. Se você tiver muitos nomes ou seus nomes entrarem em conflito, precisará refatorar.

É realmente bastante redundante.

DeadMG
fonte
7
Além disso: um IDE saudável deve tornar visualmente distintos os campos e as variáveis ​​/ parâmetros locais. Por exemplo, no Eclipse (por padrão), os campos são azuis, enquanto as variáveis ​​locais são pretas.
Joachim Sauer
11
@Joachim Bom ponto, o Eclipse pode até colorir parâmetros e variáveis ​​locais de maneira diferente se o usuário desejar (no entanto, isso não é o padrão).
Eric-Karl
3
Embora eu concorde, ao encontrar o código de outros desenvolvedores (e ao mesmo tempo não estar familiarizado), acho this.muito mais útil. Provavelmente também é porque eu não tenho um IDE que codifique as variáveis ​​locais / objetos de cores de maneira diferente.
Brad Christie
3
+1 para (paráfrase) "refatorar se você precisar usar isso para deduzir que é um membro". Exatamente o que eu queria destacar.
Yam Marcovic 11/11
Não acho que seja mais difícil ler e, em troca, o código permanece legível em editores que possuem destaque de sintaxe menos sofisticado que não distingue entre campos e locais. Eu sempre tive a opinião de que você deve se esforçar para que seu código seja facilmente legível no editor de texto mais básico e, se não for, deve haver uma boa razão para isso.
Kevin
26

Eu prefiro usar this. Isso facilita a leitura de código em vários editores que colorem variáveis ​​locais e de instância da mesma maneira. Também facilita a leitura do código em uma página impressa durante algo como uma revisão de código. Também é um lembrete bastante forte sobre o escopo da variável para outros desenvolvedores.

No entanto, existem argumentos contra isso. Nos IDEs modernos, você pode descobrir o escopo de uma variável passando o mouse sobre ela ou visualizando-a em uma estrutura semelhante a uma árvore. Você também pode alterar a cor e / ou a fonte das variáveis, dependendo do escopo (mesmo que, quando impressas, seja evidente qual é o escopo da variável).

Acredito que a última frase de ChrisF esteja morta: seja consistente em seu uso.

Thomas Owens
fonte
7
"Também é um lembrete bastante forte quanto ao escopo da variável para outros desenvolvedores". - o motivo pelo qual eu uso e gosto de ver this.no código. Demora meio segundo para escrever e pode economizar longos minutos ao descobrir se o cara antes de você realmente pretendia usar a propriedade pascal-case em vez do local camel-case lá quando ele fez essa última explosão de mudanças há 20 revisões.
scrwtp
18

Um lugar que eu sempre uso 'this' é setters e / ou construtores:

public void setFoo(String foo) {
    this.foo = foo;
}

Fora isso, não acho necessário adicioná-lo. Ao ler o corpo de um método, os parâmetros e os locais estão lá - e razoavelmente fáceis de acompanhar (mesmo sem a ajuda do IDE). Também locais e campos tendem a ser de natureza diferente (estado do objeto versus armazenamento ou parâmetro transitório).

Se houver alguma confusão sobre o que é uma variável e o que é um campo, provavelmente significa que um método tem muitas variáveis ​​/ parâmetros, é muito longo e muito complexo e deve ser simplificado.

Se você optar por usar 'this' para marcar os campos, eu recomendaria garantir que a convenção seja sempre rigorosamente seguida - seria muito fácil começar a supor que 'this' significa que é uma coisa local e importante baseada na suposição.

edit: Eu também acabo usando isso em equals, clone ou qualquer coisa que tenha um parâmetro 'that' do mesmo tipo de objeto:

public boolean isSame(MyClass that) {
    return this.uuid().equals(that.uuid());
}
ptyx
fonte
8

É discutível.

Tomando C # como analogia, pois possui uma sintaxe e estrutura muito semelhantes às Java, descobrimos que o C # StyleCop possui uma regra padrão que insiste em adicionar this, mas o ReSharper possui uma regra padrão que diz que thisé redundante (o que é) e pode ser removido.

Portanto, se você estiver usando uma ferramenta, você as adicionará, mas se você usar outra, as removerá. Se você estiver usando as duas ferramentas, terá que escolher e desativar uma das regras.

No entanto, o que as regras realmente significam é que você é consistente em seu uso - o que provavelmente é a coisa mais importante.

ChrisF
fonte
8

É uma prática ruim sempre acrescentar isso aos atributos da instância atual?

Sim - por alguns, não - por outros.

Eu gosto e uso thispalavras-chave em meus projetos em Java e C #. Pode-se argumentar que o IDE sempre destacará parâmetros e campos por cores diferentes, mas nem sempre trabalhamos no IDE - temos que fazer várias combinações / diferenças / algumas alterações rápidas em um bloco de notas / verificar alguns trechos de código no email . É muito mais fácil identificar, desde o primeiro olhar, onde o estado da instância é alterado - por exemplo, revisar alguns possíveis problemas de simultaneidade.

Andrey Taptunov
fonte
7

Eu acho que se você precisar usar isso, você tem um método que é muito longo ou uma classe que está tentando fazer muito, ou ambos.

Os métodos nunca devem ter mais do que algumas linhas de código, use uma ou duas variáveis ​​locais, determinando o que é que se torna fácil; mesmo com apenas o contexto de 3 linhas da maioria das ferramentas diff. Se seus métodos são muito longos e suas classes têm muitas responsabilidades (geralmente significando muitos campos), a solução é dividi-los.

Eu acho que "isso" apenas desorganiza o código. Especialmente com IDEs modernos que irão colorir parâmetros / variáveis ​​locais / campos locais de maneira diferente.

Eric-Karl
fonte
5

Eu acho que você respondeu sua própria pergunta com isso:

Parece mais natural para mim escrever

... isso ...

do que

... foo ...

pois me ajuda a distinguir atributos de instância de variáveis ​​locais.

Se você se sentir mais à vontade para usar this.enquanto aprimora seu conhecimento de trabalho com Java, use de qualquer maneira ( acho que é, de certa forma, o familiar Python a que você está se relacionando ).

O fato é que, embora as pessoas dêem argumentos sólidos / pertinentes sobre o uso ou não this., ainda soa como um debate, exemplo dado:

  • torna claro o propósito das variáveis vs. você deve reescrever o código se não estiver claro o que é cada variável;
  • this.é redundante se você passa o dia inteiro no IDE vs. eu executo revisões de código e faço diferenças em versões diferentes usando um comparador sem destaque de sintaxe;
  • não digitar this.me ganha milissegundos importantes de produtividade vs. sou pago pela tecla pressionada e adicionar this.é como um aumento salarial: D;
  • etc etc

Mas o ponto principal é que, no final do dia, ele ainda volta à preferência pessoal e ao ambiente de trabalho .


fonte
5

Normalmente, adicionar isso é desnecessário. Eu não acho que seja uma prática ruim por si só, mas o uso excessivo disso provavelmente seria considerado incomum na maioria das bases de código Java que eu já vi.

No entanto, acho valioso em algumas situações específicas:

Substituindo parâmetros locais - às vezes é necessário especificar que você deseja usar uma variável de instância em vez de uma variável de parâmetro / local com o mesmo nome. Isso é bastante comum em construtores, nos quais você deseja que o nome do parâmetro corresponda ao nome interno da variável de instância que é usada para inicializar, por exemplo

class MyObject {
  int value;

  public MyObject(int value) {
    this.value=value;
  }
}

Ao lidar com outras instâncias da mesma classe - acredito que torna o código mais claro e compreensível para ser explícito a qual instância da classe você está se referindo, por exemplo

class MyObject {
  int value;
  ....

  public MyObject add(MyObject other) {
    return new MyObject( this.value + other.value )
  }
}
Mikera
fonte