Hoje veremos como podemos evitar o uso do else para escrever um código mais legível usando a linguagem C#. |
De acordo com Robert C. Martin, a definição de
código limpo não é muito bem definida, no entanto, os resultados do código limpo
são bastante claros. Você quer que o código seja legível como um bom livro,
fácil de manter e fácil de estender.
Os bugs devem ser facilmente detectáveis ou até mesmo evitados pelo design. Um código limpo manterá a produtividade alta e os custos de manutenção baixos.
Para outros
desenvolvedores manterem seu código, ele deve ser extremamente fácil de ler e
entender. Seu objetivo, ao escrever qualquer linha de código, deve sempre ser
legibilidade. Mesmo uma linha pode confundir outro desenvolvedor o suficiente
para que ele perca minutos preciosos entendendo seu código, e a culpa é sua!
Então, o que torna um código mais legível por outros desenvolvedores?
Neste artigo, veremos algumas dicas para escrever um código mais curto e legível possível de forma que elas complementam as demais diretrizes que ditam o código limpo. Cabe a você avaliar cada uma delas e verificar se a sua aplicação faz sentido para você.
Assim você deverá analisar o seu código e verificar se nos blocos de códigos que usam if-else o uso do else esta sendo feito de forma redundante. Se este for o caso esses blocos else redundantes tornam o seu código desnecessariamente longo, menos legível e o faz parecer mais complexo do que realmente é.
Evite usar else
A ideia é evitar o uso
excessivo da palavra-chave else
ao escrever condicionais, e isso é possível em muitos cenários.
Podemos evitar o uso do else em uma boa
parte dos cenários onde ele é usado, tornando o código mais legível e mais
enxuto.
Exemplo trivial:
a- Com else
public void
Demo1(Teste teste) { if (teste == null) { throw new ArgumentNullException(nameof(teste)); } else { //Código } } |
b- Sem else
public void
Demo2(Teste teste) { if (teste == null) throw new ArgumentNullException(nameof(teste));
//Código |
Temos aqui o que é conhecido como retorno antecipado. Você deve sempre declarar claramente o que espera dos argumentos nas primeiras linhas de código.
De forma geral estamos aumentando a complexidade ao incluir qualquer novo requisito condicional usando if-else. Uma forma de evitar o uso do if-else é definir objetos de estado que pode ser feito aplicando o padrão de projeto State.
Com isso temos os seguinte benefícios:
Exemplo:
a- Com else
public Resultado
Demo(MinhaEnum menum) { if (menum == MinhaEnum.A) { //codigo1 } else { //codigo2 } } |
b- Sem else
public Resultado
Demo(MinhaEnum menum) { return menum switch { MinhaEnum.A => Metodo1(), MinhaEnum.B => Metodo2(), _ => throw new NotImplementedException() }; Resultado Metodo1() { } Resultado Metodo2() { } } |
Aqui estamos alternando instruções usando o recurso da correspondência de padrões (pattern matching). Com isso temos uma visão clara do que acontece quando algum caso explícito foi passado e qual função esta tratando o caso. Além disso estamos criando um método para cada lógica separando as responsabilidades.
Como evitar o uso do else
-Usando return
Vejamos uma estrutura clássica usando if-else que avalia uma condição :
if (Condição)
{
// 10 linhas de código
}
else
{
// mais código
}
|
Em vez de usar este bloco podemos optar por usar um return e isso nos ajuda a se livrar do bloco else evitando código desnecessário.
if (Condição)
{
// 10 linhas de código
}
// mais código
|
-Usando valores padrão (default)
As instruções if-else são muito usadas para atribuir variáveis - o que não faz sentido. Você provavelmente já viu um código como este antes:
if (Condicao) { numero = valor * 2; } else { numero = 1 } |
Quando você identificar um código como este, altere-o. A maneira de se livrar do bloco else é atribuir um valor padrão.
numero = 1
if (Condicao) |
O código ficou mais simples e neste caso temos duas vantagens:
Ao usar um valor padrão a variável esta disponível fora da instrução if-else;
Temos menos linhas de código e o código ficou mais legível;
Ainda existe uma forma de otimizar o código
ainda mais usando apenas uma linha de código através do operador condicional
ou ternário :
numero = Condicao ? valor * 2 : 1; |
-Usando Guard Clauses
Uma Guard Clause
ou cláusula de guarda é uma verificação de pré-condições de integridade
usada para evitar erros durante a execução. Ele ajuda você a simplificar o
código removendo condições de ramificação aninhadas inúteis e retornando erros
significativos.
Para conseguir isso na plataforma .NET você pode usar uma biblioteca ou escrever
o seu próprio código defensivo.
As cláusulas de guarda também são conhecidas como
retornos antecipados. A ideia por trás do retorno antecipado é que você
escreva funções que retornem o resultado positivo esperado no final da função.
O restante do código, na função, deve acionar o encerramento o mais rápido
possível em caso de divergência com o propósito da função.
Exemplo:
public Resultado
Metodo() { if (!condicao) { return; } // código } |
Como alternativa podemos também inverter a cláusula de guarda :
public Resultado
Metodo() { if (condicao) { // código } } |
Existem outros fatores que poderíamos abordar relacionados com este assunto mas essas dicas já vão ajudar a melhorar o seu código e torná-lo mais legível.
E estamos conversados
...
"Revesti-vos, pois, como eleitos de Deus, santos e amados, de entranhas de
misericórdia, de benignidade, humildade, mansidão, longanimidade;"
Colossenses 3:12
Referências: