quinta-feira, 14 de abril de 2011

Conhecendo a classe Exception

Fonte: www.activedelphi.com.br

Durante a execução de uma aplicação é muito comum ocorrer erros que acabam atrapalhando sua execução, tais erros são denominados exceções. Por exemplo, temos uma função responsável em dividir dois valores, exemplificada abaixo:
function Divisao(Valor1,Valor2: Double): Double;
begin
  Result := Valor1/Valor2;
end;

Se atribuirmos ao parâmetro Valor2 o numero 0, irá ocorrer uma exceção e uma mensagem será exibida.

A mensagem nos informa que ocorreu uma exceção do tipo "EZeroDivide" com a mensagem "Floating point division by zero" (Divisão de ponto flutuante por zero), ou seja, tentamos dividir um valor por zero, o que na matemática é uma operação indeterminada.

O problema é que na maioria das vezes tais exceções provocam o encerramento da aplicação de forma brusca, que é muito desagradável, principalmente quando seu programa exige que determinadas informações sejam atualizadas, como salvar alterações feitas em bancos de dados. Para resolver este problema podemos utilizar a classe Exception, através das cláusulas try...except...end, de acordo com a sintaxe abaixo:
try
  //Insira aqui o bloco de comandos
except
  //Insira aqui o bloco de comandos que deverá ser executado caso ocorra alguma
  //exceção no código acima
end;
Você também pode usar o bloco try...finally...end:

try
  //Insira aqui o bloco de comandos
finally
  //De forma análoga, insira aqui o bloco de comandos que deverá ser executado caso
  //ocorra alguma exceção ou interrupção (exit / abort) no código acima
end;
Antes de prosseguirmos vamos conhecer um pouco mais a classe Exception.

A classe Exception é codificada na Unit SysUtils, é derivada da classe TObject e compõe a classe-base para todas as outras que manipulam exceções. Uma curiosidade é que a classe não segue o padrão do Delphi, onde o nome das classes deve ser precedido pela letra "T". Ela possui dois campos internos:

- um deles é o FMessage, um campo do tipo string(texto) que define a mensagem que será exibido na caixa de diálogo quando a exceção é gerada.
- o outro é o FHelpContext, do tipo integer(inteiro) que guarda o índice que identifica o tópico do arquivo help on-line associado a essa classe.

Voltando a nossa função "divisao", podemos tratá-la da seguinte forma:
function Divisao(Valor1,Valor2: Double): Double;
begin
  try
    Result := Valor1/Valor2;
  except
    ShowMessage('Valores incorretos!');
  end;
end;
Também podemos verificar qual o tipo de exceção foi gerado, usando o comando:

  on < tipo de exceção> do
Dessa forma é possível definir um bloco de comandos para cada exceção que sua aplicação possa gerar, permitindo um tratamento individual. Poderíamos redefinir a função como abaixo:

function Divisao(Valor1,Valor2: Double): Double;
begin
  try
    Result := Valor1/Valor2;
  except
    on EZeroDivide do
      ShowMessage('Divisão por zero!');
  end;
end;
Abaixo segue uma tabela com algumas exceções, claro que existe um número muito maior e é impossível lista-las. O objetivo desse artigo foi introduzir os conceitos referentes à classe Exception para quem nunca teve contato com ela.

Exceção
Significado
EZeroDivide
Divisão de um número real por zero
EDivByZero
Divisão de um número inteiro por zero
ERangeError
O limite de um número inteiro foi excedido
EIntOverFlow
O limite do resultado de uma operação com número inteiro foi excedido
EOverFlow
O limite do resultado de uma operação com numero real foi excedido
EInvalideOp
Operação inválida
EAccessViolation
Acesso violado
EDataBaseError
Erro genérico no banco de dados
EDBEngineError
Problema com a BDE
EOutOfMemory
Memória insuficiente


Você pode conferir mais sobre o uso dos comandos Try..Except e Try..Finally nesta série de artigos feita pelo João Marcos:
Try..Except..Finally - Parte 01 
Try..Except..Finally - Parte 02 
Try..Except..Finally - Final

2 comentários:

  1. O uso excessivo de Exceptions pode ocasionar lentidão em sistemas acima de 50mb?

    ResponderExcluir
    Respostas
    1. Boa tarde,

      Nunca fiz este teste, então não tenho te afirmar isso.

      Obrigado pela pergunta.

      Excluir