Carlos Rocha Posted September 13, 2013 at 11:23 AM Report #524430 Posted September 13, 2013 at 11:23 AM Bom Dia Humberto. Preciso testar dentro de um try 2 coisas: Se uma data é valida e se ela é maior ou igual à data de hoje. Se alguma dessas situaçoes ocorrerem avisar que a data é errada. Mas não esta dando certo com o codigo abaixo. Qual será o erro? Function TfrmPrincipal.DataIdade(DataNascimento : String) : Double; begin try strtodate(DataNascimento); //-- Verifica se a data é valida strtodate(DataNascimento)>= Date; except messagedlg('Data de nascimento inválida!', MTERROR, [MBOK], 0); abort; end; result := (Date - Strtodate(DataNascimento))/365.25; end; A ideia é saber se a data: 1) Esta no padrão 2) Válida menor que a data de hoje 3) Calcular a idade em anos e em meses à partir da data de nascimento informada. A função de conversão que estou usando esta dando erro direto: function TfrmPrincipal.IdadeExtenso(Idade:Double):String; var IdadeAno,IdadeMes, textoAno, textoMes: String; begin Idade:= StrToFloat(FormatFloat('0.00',Idade)); IdadeAno:= IntTostr(trunc(Idade)); IdadeMes:= copy(FloatTostr(Idade), length(FloatTostr(Idade)) -1, length(FloatTostr(Idade))); IdadeMes:= intTostr( round( (12 * strToint(IdadeMes)) / 100 ) ); textoAno:=' Anos e '; textoMes:=' Mes(es).'; if IdadeMes='0' then begin textoAno:=''; textoMes:=''; IdadeMes:=''; end; result:= IdadeAno + textoAno + IdadeMes + textoMes; end; function TfrmPrincipal.retornaIdade():Double; var DataNascimento:string; begin DataNascimento:=copy (EditDataNascimento.text,1,2) + '/' + copy (EditDataNascimento.text,3,2) + '/' + copy (EditDataNascimento.text,5,4); result:= DataIdade(DataNascimento); end;
nunopicado Posted September 13, 2013 at 02:36 PM Report #524473 Posted September 13, 2013 at 02:36 PM Duas coisas: strtodate(DataNascimento)>= Date; Esta linha, por causa dos operadores, é uma expressão, e como tal, não pode estar isolada numa instrução. Deves declarar uma variavel do tipo boolean, e atribuir à variável o resultado. var b:Boolean; . . . b:=strtodate(DataNascimento)>= Date; Segundo: Ao fazeres a gestão de excepções num try...except, as excepções não desaparecem. São levantadas ainda assim. O que acontece é que antes do teu código de tratamento as apanhar, o Debugger do Delphi/Lazarus apanha-as. Quer isto dizer que, para veres correctamente o comportamento do teu programa a gerir as excepções, tens de: a) Em vez de correr o programa a partir do IDE, chama-o directamente no sistema operativo. Isto faz com que a única gestão de excepções a correr para o teu programa seja o proprio programa, e portanto, já não te dá um erro prévio ao que tu determinaste. b) Ao executar pelo IDE, quando der o erro, escolhe a opção Continuar. O debugger deixa passar o erro, e de seguida será o código do Except a ser executado. "A humanidade está a perder os seus génios... Aristóteles morreu, Newton já lá está, Einstein finou-se, e eu hoje não me estou a sentir bem!" > Não esclareço dúvidas por PM: Indica a tua dúvida no quadro correcto do forum.
armizimm Posted September 15, 2013 at 12:10 PM Report #524622 Posted September 15, 2013 at 12:10 PM (edited) E assim? Function TfrmPrincipal.DataIdade(DataNascimento : String) : Double; begin try strtodate(DataNascimento); //-- Verifica se a data é valida If (strtodate(DataNascimento) >= Date) then StrToInt('A'); // O correto não seria gerar a exceção, mas mostrar outra mensagem no lugar de StrToInt('A') colocar um ShowMessage(' Data inválida! '); except messagedlg('Data de nascimento inválida!', MTERROR, [MBOK], 0); abort; end; result := (Date - Strtodate(DataNascimento))/365.25; end; Edited September 15, 2013 at 12:42 PM by nunopicado Adicionada linguagem GeShi
nunopicado Posted September 15, 2013 at 12:49 PM Report #524625 Posted September 15, 2013 at 12:49 PM (edited) Dar dá... Mas aquela forma de chamar uma excepção é muito pouco elegante, especialmente quando tens métodos próprios para o efeito. Function Tform1.DataIdade(DataNascimento : String) : Double; begin try If (strtodate(DataNascimento) >= Date) then raise Exception.Create(''); except messagedlg('Data de nascimento inválida!', MTERROR, [MBOK], 0); abort; end; result := (Date - Strtodate(DataNascimento))/365.25; end; Também dispensas a primeira linha, porque ao testar se é maior que a data actual, se for inválida já vai haver excepção de qualquer maneira. Edited September 15, 2013 at 12:51 PM by nunopicado "A humanidade está a perder os seus génios... Aristóteles morreu, Newton já lá está, Einstein finou-se, e eu hoje não me estou a sentir bem!" > Não esclareço dúvidas por PM: Indica a tua dúvida no quadro correcto do forum.
Carlos Rocha Posted September 15, 2013 at 06:28 PM Author Report #524640 Posted September 15, 2013 at 06:28 PM (edited) Ok If (strtodate(DataNascimento) >= Date) Mas e se data chegar até aqui com um formato irregular? Tipo 12-06-99. strtodate(DataNaciento)>= Date testa isso também? Edited September 15, 2013 at 09:51 PM by thoga31
nunopicado Posted September 15, 2013 at 06:37 PM Report #524641 Posted September 15, 2013 at 06:37 PM Sim. Antes do compilador efectuar a operação strtodate(DataNascimento) >= Date, tem de calcular o valor retornado por strtodate(DataNascimento), para que possa depois comparar se é ou não maior. Ao calcular este resultado, se a data for inválida, dá imediatamente erro, e já não chega a comparar com a data. Este erro é uma excepção do tipo EConvertError, que será apanhada pelo Try...Except. "A humanidade está a perder os seus génios... Aristóteles morreu, Newton já lá está, Einstein finou-se, e eu hoje não me estou a sentir bem!" > Não esclareço dúvidas por PM: Indica a tua dúvida no quadro correcto do forum.
Carlos Rocha Posted September 16, 2013 at 04:48 PM Author Report #524765 Posted September 16, 2013 at 04:48 PM Pois é. Aí é que esta o problema. Eu preciso fazer duas verificações no try. Uma pra verificar se esta errado ou não o formato da data E outra para verificar a regra de negocio que diz que a data não pode ser superior à data de hoje. Isso é possível em um só try(como)? Ou terei que usar 2 try's? Aí fica esquisito não?
nunopicado Posted September 16, 2013 at 04:55 PM Report #524768 Posted September 16, 2013 at 04:55 PM Não seria esquisito, porque o Try é uma estrutura encadeável. Podes usar um try...except dentro de um try...finally, por exemplo. Mas neste caso, nem é preciso, porque estás à procura de excepções num só bloco de código, pelo que basta um try. Caso a mensagem a mostrar ao utilizador seja a mesma ("Data Inválida"), basta manter como está. Caso quisesses mensagens diferentes, aí sim, podias por dois try...except, ou melhor ainda, usar códigos de excepções diferentes e com um IF no Except a definir a mensagem. "A humanidade está a perder os seus génios... Aristóteles morreu, Newton já lá está, Einstein finou-se, e eu hoje não me estou a sentir bem!" > Não esclareço dúvidas por PM: Indica a tua dúvida no quadro correcto do forum.
nunopicado Posted September 16, 2013 at 05:15 PM Report #524772 Posted September 16, 2013 at 05:15 PM (edited) Por exemplo: Function DataIdade(DataNascimento : String) : Double; begin try If (strtodate(DataNascimento) >= Date) then raise Exception.Create(''); except on E: EConvertError Do messagedlg('Data de nascimento inválida!', MTERROR, [MBOK], 0); else messagedlg('Novo demais!', MTERROR, [MBOK], 0); abort; end; result := (Date - Strtodate(DataNascimento))/365.25; end; Edited September 16, 2013 at 05:27 PM by nunopicado "A humanidade está a perder os seus génios... Aristóteles morreu, Newton já lá está, Einstein finou-se, e eu hoje não me estou a sentir bem!" > Não esclareço dúvidas por PM: Indica a tua dúvida no quadro correcto do forum.
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now