C# - 10 dicas para otimizar o seu código


A otimização do código de uma aplicação é um aspecto importante que contribui para melhorar o desempenho e a eficiência.

A seguir temos 10 dicas rápidas, mas importantes, que quando aplicadas ao seu dia dia ajudam a otimizar o código de sua aplicação C#.

1- Utilizando o StringBuilder de forma adequada

O objeto String é imutável e cada vez que você usa um dos métodos da classe System.String você cria um novo objeto string na memória que requer uma nova alocação de espaço para o novo objeto.

Em situações onde você precisa realizar repetidas modificações em um string, a criação de um novo objeto String tem um custo elevado.

Ai entra o objeto StringBuilder, você já deve saber que o objeto StringBuilder é muito mais rápido para concatenar strings principalmente quando temos strings grandes.

Dessa forma se você tem que concatenar strings em um laço com muitas iterações a classe System.Text.StringBuilder é imbatível.

Mas atenção, se você pretende concatenar apenas uma única string então ao invés de usar o StringBuilder de preferência ao tipo String simples; nestes casos usar strings é mais recomendado:

Para strings grandes ou operações repetidas com strings ao invés de usar:

  string msg;
  msg = msg + "macoratti.net";
  msg = msg + "Otimize seu código C#";
  msg = msg + " ......";
  msg = msg + " ......";
  msg = msg + "Utilizando o StringBuilder";

prefira usar:

  StringBuilder msg = new StringBuilder();
  
  msg.Append("macoratti.net ");
  msg.Append("Otimize seu código C# ");
  msg = msg + " ......";
  msg = msg + " ......";
  msg.Append("Utilizando o StringBuilder ");
 
mas para operações simples com strings não use StringBuilder prefira usar strings:

  string msg;
  msg = msg + "macoratti.net";

2- Comparando Strings Non-Case-Sensitive

Muitas vezes temos que comparar duas variáveis strings, sem considerar o case sensitive. O recurso mais usado é converter ambas as strings para caixa baixa (minúsculas) ou caixa alta (maiúsculas) e então comparar as duas strings da seguinte forma:

str1.ToLower() == str2.ToLower()

Porém usar repetidamente a função ToLower() afeta o desempenho.

Uma escolha melhor é usar a função string.Compare() .

Assim podemos fazer:

string.Compare(str1, str2, true) == 0

A função string.Compare() retorna um inteiro que é igual a 0 quando as duas strings forem iguais.

3- Utilize String.Empty ao invés de ""

A sugestão em usar string.Empty não é tanto pelo fator desempenho mas para facilitar a leitura e entendimento do seu código.

Ao invés de usar:

if (str1 == "")

prefira usar:

if (str1 == string.Empty)

É uma boa prática de programação e não causa um impacto negativo no desempenho da aplicação.

4- Prefira utilizar List<> a ArrayList

Um ArrayList é útil quando desejamos armazenar mais de um tipo de objeto em uma mesma lista. Porém se desejamos tratar o mesmo tipo de variável em um ArrayList podemos ter um desempenho melhor usando a classe List<>.

Dessa forma no código abaixo:

ArrayList intLista = new ArrayList();
intLista.add(10);
return (int)intLista[0] + 20;

Temos que a nossa lista contém apenas inteiros. Neste caso usar a classe List<> é muito melhor. Para convertê-la para uma lista tipada, somente os tipos das variáveis necessitam ser alterados;

List<int> intLista = new List<int>();
intLista.add(10)
return intLista[0] + 20;

Não precisamos realizar uma conversão forçada (cast) com List<>.

O aumento do desempenho pode ser especialmente significativo com dados primitivos como Integers.

5- Utilize os operadores && e || ao invés de & e |

Ao tratar com instruções if no seu código, utilize os operadores && e || com dupla notação (AndAlso e OrElse no Visual Basic).

Instruções if que usam & e | preciam verificar cada parte da instrução e então aplicar o 'and' ou 'or'.

Ao usar && e || o compilador percorre a instrução somente uma única vez e para assim que a condição foi verificada verdadeira ou falsa.

Considere o seguinte código:

if (object1 != null && object1.runMethod())

Se o object1 é nulo , com o operador &&,  object1.runMethod() não será executado.

Se o operador usado for &, object1.runMethod() será executado mesmo se  object1 for nulo, causando um exceção.

6- Use o bloco Try-Catch ao invés de if

O bloco Try-Catch é usado para capturar exceções que vão além do controle do programado, como conexões com banco de dados ou dispositivos de rede.

Então dê preferência a usar o  bloco Try-Catch para capturar exceções ao invés de usar instruções if.

static void Main()
{
   int x;
   try
   {
      
// Não inicialize a variável aqui
      x = 123;
   }
   catch
   {
   }
    
// Erro: Uso de uma variável local não atribuída
    Console.Write(x);
}

No interior de um bloco try somente inicialize uma variável que for declarada dentro do bloco, de outra forma poderá ocorrer uma exceção antes que execução do bloco terminar. O exemplo acima mostra isso.

7- Substitua operações de divisão por shift/Multiplicação

O C# é lento com operações de divisão, uma alternativa é substituir essas operações pela utilização do operador Shift e uma operação de multiplicação.

Exemplo:

x = num / div;   

Deve ser substituído por:

        x = (num * mul) >> shift;

O operador de multiplicação e o operador shift é mais rápido que a divisão.

Assim outras operações como mod também podem ser otimizadas usando o mesmo princípio:

x = num % div;   é igual a  x = num - (num/div) * div;

que deve ser substituído por:

x = num - ((num * mul) >> shift) * div;

8- O Laço for é mais rápido que laço foreach

Prefira usar um laço for a um laço foreach.

Ao invés de usar:

static private void TestForeachLoop(ArrayList List)
{
   int id = 0;

   foreach (int i in List)
   {
      // processamento...
     id = i;
    }
}
laço foreach é mais lento

 Prefira usar:

static private void TestForLoop(ArrayList List)
{
    int id = 0;
    int count = List.Count;

    for (int i = 0; i < List.Count; i++)
    {
       // processamento...
       id = (int)List[i];
    }
}
laço for é mais rápido
9 - Heap x Stack. Stack é mais rápido.

A alocação de memória para estruturas(Stack) é muito mais rápida que alocação de memória para Classes(Heap).

Quando  possível evite criar objetos e usar classes prefira usar os tipos primitivos e estruturas. (quando possível...)
10 - String.Equals é melhor que == 

O  operador == é fortemente tipada e somente será compilado se ambos os parâmetros forem strings oque implica que não há necessidade de realizar conversão.

String.Equals possui múltiplas sobrecargas, uma delas é fortemente tipada, e, dependendo da versão que você chama você pode pagar um custo por isso

Obs: Para comparar strings ,que são valores por referência, use String.Equals. Ex: string.Equals(s1, s2)

São 10 dicas simples mas que se usadas sistematicamente tornam o seu código mais eficiente e rápido.

C# , Simples, simples assim...

Veja os Destaques e novidades do SUPER DVD Visual Basic (sempre atualizado) : clique e confira !

Quer migrar para o VB .NET ?

Quer aprender C# ??

Quer aprender os conceitos da Programação Orientada a objetos ?

Quer aprender o gerar relatórios com o ReportViewer no VS 2013 ?

  Gostou ?   Compartilhe no Facebook   Compartilhe no Twitter

Referências:


José Carlos Macoratti