Halt(0); ou Application.Terminate???

Delphi

09/02/2006

como diz o título qual a melhor opção?


Paullsoftware

Paullsoftware

Curtidas 0

Melhor post

Marco Salles

Marco Salles

09/02/2006

Pera ai Uma coisa é finalizar a aplicação outra coisa e forçar com que a aplicação feche imediatamente...


desculpe , esta ultima colocaçao para o PaullSoftware

simples assim... então pra que existem essas opções!


e não tem relação com a resposta do cabelo

Com relação a resposta do cabelo

Se não me engano... A função Halt(); é utilizada para fechar TODOS os forms de um determinado nível, indicado pelo número que passamos como parâmetro... exemplo... se tiver 5 forms abertos... sendo 1 principal, outros 2 como filhos e mais dois como netos... se desejar fechar os forms do 3º nível, então dou um Halt(2).. E ASSIM POR DIANTE...


Acho que não procede isto.. :cry: :cry: :cry:


GOSTEI 1

Mais Respostas

Rjun

Rjun

09/02/2006

Nenhuma. Use o Close do seu form principal.


GOSTEI 0
Paullsoftware

Paullsoftware

09/02/2006

Nenhuma. Use o Close do seu form principal.

simples assim... então pra que existem essas opções!


GOSTEI 0
Cabelo

Cabelo

09/02/2006

Se não me engano...

A função Halt(); é utilizada para fechar TODOS os forms de um determinado nível, indicado pelo número que passamos como parâmetro...

exemplo... se tiver 5 forms abertos... sendo 1 principal, outros 2 como filhos e mais dois como netos...

se desejar fechar os forms do 3º nível, então dou um Halt(2).. E ASSIM POR DIANTE...

Já o método terminate, fecha a aplicação, independente de onde você está chamando-a, sem dar erro. Pois esse método elimina da mamória todos os forms e componentes criados pela aplicação.


GOSTEI 1
Marco Salles

Marco Salles

09/02/2006

Pera ai

Uma coisa é finalizar a aplicação outra coisa e forçar com que a aplicação feche imediatamente...


GOSTEI 0
Rjun

Rjun

09/02/2006

Halt ou Terminate server para interrromper a execução do aplicativo. Se você quer terminar a execução, tipo um menu close, utilize o close do seu form principal.

O Halt interrompe de forma abrupta a execução. O número entre parenteses é um código de erro que pode ser capturado pela variavel ERRORLEVEL do SO. Esse código de erro eu utilizava em arquivos .BAT.


GOSTEI 0
Michael

Michael

09/02/2006

Existem diferenças não-triviais entre o método [b:63eecd0c7d]Terminate [/b:63eecd0c7d]e [b:63eecd0c7d]Halt[/b:63eecd0c7d].

[b:63eecd0c7d]Halt [/b:63eecd0c7d]fecha a aplicação de forma anormal, não liberando a memória alocada pelos objetos, recursos consumidos, etc. O seu único parâmetro é o [b:63eecd0c7d]ExitCode [/b:63eecd0c7d]retornado ao sistema operacional, e não tem relação com a quantidade de forms abertos.

[b:63eecd0c7d]Terminate [/b:63eecd0c7d]fecha a aplicação, assegurando que tudo que foi alocado seja liberado. Em outras palavras, chama o método [b:63eecd0c7d]Free [/b:63eecd0c7d]para todos os componentes, que chamarão [b:63eecd0c7d]Free [/b:63eecd0c7d]para os componentes que são seus ´filhos´ (definidos através do parâmetro [b:63eecd0c7d]Owner [/b:63eecd0c7d]no construtor). Também dispara uma mensagem para o Windows, para garantir que tudo seja destruído na ordem certa. Por essa razão [b:63eecd0c7d]Terminate [/b:63eecd0c7d]pode demorar alguns segundos para fechar a aplicação, enquanto [b:63eecd0c7d]Halt [/b:63eecd0c7d]é imediato.

Existe a propriedade [b:63eecd0c7d]Terminated[/b:63eecd0c7d], da classe [b:63eecd0c7d]TApplication[/b:63eecd0c7d], que pode ser usada para saber se a aplicação está em processo de shut down. Isso pode ser útil para não executar nenhum código quando a aplicação estiver sendo finalizada.

O método [b:63eecd0c7d]Close [/b:63eecd0c7d]da classe [b:63eecd0c7d]TCustomForm [/b:63eecd0c7d]chama [b:63eecd0c7d]Application.Terminate[/b:63eecd0c7d] caso o formulário seja o [b:63eecd0c7d]MainForm [/b:63eecd0c7d]da aplicação. Portanto, ambos têm o mesmo efeito nesse caso.

Portanto, na maioria dos casos, use [b:63eecd0c7d]Terminate [/b:63eecd0c7d]ou [b:63eecd0c7d]Close[/b:63eecd0c7d], se o form for o principal.


GOSTEI 0
Marco Salles

Marco Salles

09/02/2006

ainda tem o exitprocess(0) que é uma função da api do Windows


GOSTEI 0
Paullsoftware

Paullsoftware

09/02/2006

Valeu galera as declarações e esclarecimento aqui encontradas foram de grande ajuda...

abraço a todos... :lol:


GOSTEI 0
Michael

Michael

09/02/2006

Caros colegas,

Gostaria de retificar algo que afirmei em meu último post neste tópico:

[b:389689a045]Halt [/b:389689a045]fecha a aplicação de forma anormal, não liberando a memória alocada pelos objetos, recursos consumidos, etc. (...)


Isso não está correto. Ao contrário do que falei, [b:389689a045]Halt[/b:389689a045] respeita os objetos criados pela aplicação, que tenha sido inicializados com o parâmetro [b:389689a045]Owner [/b:389689a045]apontando para algo gerenciado pelo aplicativo, como o formulário principal. Desta forma chamar [b:389689a045]Halt [/b:389689a045]não irá deixar memória desalocada desnecessariamente. É claro que o sistema operacional pode não repor totalmente a memória consumida, mas isso tbm poderia ocorrer com [b:389689a045]Terminate[/b:389689a045].

Constatei meu erro ao ler a documentação do Delphi e após umas ´olhadas´ no código fonte da VCL. ;-)

Bom, corrigido! :-D

[]´s[b:389689a045][/b:389689a045]


GOSTEI 0
Martins

Martins

09/02/2006

Caros colegas, Gostaria de retificar algo que afirmei em meu último post neste tópico: [quote:a0d3eef0bf=´Michael´][b:a0d3eef0bf]Halt [/b:a0d3eef0bf]fecha a aplicação de forma anormal, não liberando a memória alocada pelos objetos, recursos consumidos, etc. (...)


Isso não está correto. Ao contrário do que falei, [b:a0d3eef0bf]Halt[/b:a0d3eef0bf] respeita os objetos criados pela aplicação, que tenha sido inicializados com o parâmetro [b:a0d3eef0bf]Owner [/b:a0d3eef0bf]apontando para algo gerenciado pelo aplicativo, como o formulário principal. Desta forma chamar [b:a0d3eef0bf]Halt [/b:a0d3eef0bf]não irá deixar memória desalocada desnecessariamente. É claro que o sistema operacional pode não repor totalmente a memória consumida, mas isso tbm poderia ocorrer com [b:a0d3eef0bf]Terminate[/b:a0d3eef0bf].

Constatei meu erro ao ler a documentação do Delphi e após umas ´olhadas´ no código fonte da VCL. ;-)

Bom, corrigido! :-D

[]´s[b:a0d3eef0bf][/b:a0d3eef0bf][/quote:a0d3eef0bf]

Blz Michael, pelo menos vc retificou a informação prestada, valew!!!


GOSTEI 0
Marco Salles

Marco Salles

09/02/2006

[b:b4368d2f50]vamos colocar mais pimenta nesse tópico[/b:b4368d2f50] :lol: :lol: :lol:

primeiro quero deixar claro que não sou e ne pretendo ser formador de opinões ... Apenas tento ser passador de informaçoes

Segue :

tirado do tópico : http://forum.devmedia.com.br/viewtopic.php?t=69850&highlight=exitprocess&sid=ad15ebb96ab9aaa0997294d3c29ab240


[b:b4368d2f50]Naquele tópico o vitor^_^ , inicia assim sua postagem :[/b:b4368d2f50]

[size=18:b4368d2f50][b:b4368d2f50][color=darkblue:b4368d2f50]o pessoal com mais experiência, Por favor, se tiver algum erro no texto abaixo, me corrijam pls ^^ [/color:b4368d2f50][/b:b4368d2f50][/size:b4368d2f50]


Há varios métodos de se terminar um programa. Para se criar uma saída ou terminação anormal no programa nós geralmente usamos a procedure halt. mas essa procedure dá varios erros porque ela passa um código de erro ao sistema operacional. Além disso, os passos da procedure logo após ela são executados, porque a procedure que a chamou retorna à sua propria procedure chamadora. talvez até tente mexer com objetos que deveriam estar destruidos. Isso que cria aquele monte de janelas de erro e aquele erro de ´enviar relatorio´ no windows XP. No windows 98 isso causa a paralização do sistema com uma ´tela azul´. [quote:b4368d2f50]Um outro problema do halt é que ele não destroi objetos, não dá free em nada, deixando a memória do windows ´Suja´.


Portanto, halt não seria apropriado para usar no meio de um programa, mas sim no caso de uma excessão no tratamento de excessoes, e mesmo assim podem ser usados outros métodos.

Se o programa não usa o objeto global application, por exemplo um programa console de loop infinito, pode-se usar o halt numa exception mas o programa ´Sai´ normalmente com um simples exit; no corpo da procedure principal do programa;

se o programa usa units com o objeto global application, pode-se usar o application.terminate. Este método funciona assim: ele chama uma lista encadeada de funções booleanas de término, executa todas e se todas retornaram true, ele executa a função de api PostQuitMessage(0); Colocando assim uma mensagem de erro zero na saida para o sistema operacional. Esse método pra terminar o programa é muito bom, mas ele tem uns probleminhas: primeiro ele termina de criar o programa inteiro, para depois terminá-lo. Isso no caso de um datamodule seria causa de vários erros se fosse executado durante o create do datamodule. Isso também dá tela azul. Um outro problema do Terminate é a lista encadeada de functions booleanas que ele executa. Geralmente a lista está vazia, mas se tiver alguma, e esta retornar false, a aplicação não termina. O terceiro problema é o seguinte: as forms e objetos filhos só são liberadas da memória no evento onclose se a closeaction for do tipo cafree, ou se é executado um release. Se todas as forms estiverem fechadas e a principal é fechada, ela é liberada e o terminate é executado automaticamente. Mas se o terminate é executado direto, deixa a memória suja, porque não libera os objetos da memoria.

Existe uma função da api do windows que termina um programa ou processo imediatamente, sem nenhum erro ou tela azul, que é o exitprocess(0); É o mais silencioso de todos, mas mantém a memória suja, porque não destroi ou libera nenhum objeto ou form. Mas faz o que tem que fazer, que é colocar o valor 0 no registrador EAX do processador. O que fazer então? Qual a melhor forma de liberar um programa da memória de maneira limpa?[/quote:b4368d2f50]

A resposta é: 

Código: 
    self.free;              //usado somente se estiver dentro de uma form ou datamodule 
    application.free;    //se o objeto application estiver disponível; 
    exitprocess(0);    //por último, pra finalizar. 



nessa ordem é garantido que ele limpa a memória, não dá tela azul e nem assusta o usuario. isso é o que pode ser usado naquelas exceptions mais ferradas, quando o programa não pode ser fechado ou finalizado normalmente mas tem que ser fechado de repente.


a pergunta é ::: como o próprio vitor^^ descreveu no tópico postado por ele

[size=18:b4368d2f50][b:b4368d2f50][color=darkblue:b4368d2f50]o pessoal com mais experiência, Por favor, se tiver algum erro no texto abaixo, me corrijam pls ^^ [/color:b4368d2f50][/b:b4368d2f50][/size:b4368d2f50]


[color=red:b4368d2f50]O que voces acham ou pensam...[/color:b4368d2f50]


GOSTEI 0
Michael

Michael

09/02/2006

Olá!

Eu pensava a mesma coisa sobre o [b:93568a241c]Halt[/b:93568a241c], até tirar a prova dos 9: Criei uma classe derivada de [b:93568a241c]TComponent[/b:93568a241c], a instanciei colocando o Form como [b:93568a241c]Owner[/b:93568a241c], sobrescrevi o destrutor e coloquei um breakpoint dentro dele. Da mesma forma que implementei o evento [b:93568a241c]OnDestroy[/b:93568a241c] do form. Executei o programa e chamei [b:93568a241c]Halt[/b:93568a241c]. Os dois breakpoints foram executados, o que significa que os destrutores das classes foram corretamente avaliados e tudo liberado da memória.

Além disso, foi o que eu citei no último post: qdo um programa termina o sistema operacional libera toda a memória que foi disponibilizada para ele. Mesmo que objetos não sejam explicitamente destruídos, o SO o fará posteriormente. Mesmo assim eu não aconselho a ninguém confiar plenamente nisso mas sim sempre liberar os objetos que forem criados manualmente.

Do mais, não se deve dar [b:93568a241c]Free[/b:93568a241c] no objeto Application, pela simples razão de ele não ter sido criado pelo programador, e sim pelo Delphi. Fazendo isso corre-se o risco de o Delphi usar o objeto posteriormente e ele não existir mais, resultado em um AV. E tbm não se o form for o principal, usa-se Close, que engatilha Application.Terminate nos bastidores.

[]´s


GOSTEI 0
Marco Salles

Marco Salles

09/02/2006

este ultimo post não foi colocado por mim , mas sim pelo amigo vitor^_^
eu so descrevi aquilo que ele passou.. Abre Aspas e fecha Aspas diga-se de passagem

A minha opinião pessoal é que as pessoas querem uma receita de bolo acreditando que existe alguma invalivel.. Hora se entre os tres processos , uma for invalivel , então as outra duas são lixo , o que acredito não ser verdade.

estes processos muitas das vezes depende de como esses forms foram criados e como eles sao construidos...

Do mais, não se deve dar Free no objeto Application, pela simples razão de ele não ter sido criado pelo programador, e sim pelo Delphi. Fazendo isso corre-se o risco de o Delphi usar o objeto posteriormente e ele não existir mais, resultado em um AV. E tbm não se o form for o principal, usa-se Close, que engatilha Application.Terminate nos bastidores.


quanto a essa afirmação , eu acho que se este aplication.free for dado no formulario principal não se obtera erro e usar o onclose não procede porque estamos falando de interrupçoes bruscas....


GOSTEI 0
Michael

Michael

09/02/2006

[quote:1eb04df937=´Marco Salles´]este ultimo post não foi colocado por mim , mas sim pelo amigo vitor^_^
eu so descrevi aquilo que ele passou.. Abre Aspas e fecha Aspas diga-se de passagem[/quote:1eb04df937]

Deixando de lado a ironia, a última frase do post é:

[color=red:1eb04df937]O que voces acham ou pensam...[/color:1eb04df937]

Presumo que foi o nobre colega quem escreveu isso.

[quote:1eb04df937=´Marcos Salles´]A minha opinião pessoal é que as pessoas querem uma receita de bolo acreditando que existe alguma invalivel.. Hora se entre os tres processos , uma for invalivel , então as outra duas são lixo , o que acredito não ser verdade.

estes processos muitas das vezes depende de como esses forms foram criados e como eles sao construidos...[/quote:1eb04df937]

Concordo. Cada caso é um caso.

[quote:1eb04df937=´Marcos Salles´]quanto a essa afirmação , eu acho que se este aplication.free for dado no formulario principal não se obtera erro e usar o onclose não procede porque estamos falando de interrupçoes bruscas....[/quote:1eb04df937]

A regra geral é que só devemos destruir o que foi criado por nós. Como o a variável global Application é inicializa pela aplicação, ela é a responsável por desalocá-la. Mesmo assim chamar Free apenas não vai interromper a execução da aplicação. Creio q deva apenas destruir os forms abertos.

Este post começou perguntando o que era melhor entre Halt, Close ou Application.Terminate. Não foi questionado sobre como terminar uma aplicação bruscamente. Em todo caso, pode-se usar a API TerminateProcess, que o Windows usa para fechar um processo instantaneamente, ou a própria ExitProcess citada inicialmente por vc. É importante notar que ambas as API´s não respeitarão os destrutores dos objetos criados, conseqüentemente eventos como OnDestroy não serão executados. Isso pode ser crítico qdo o código neles for essencial para algum processo.

[]´s


GOSTEI 0
Marco Salles

Marco Salles

09/02/2006

Deixando de lado a ironia, a última frase do post é: O que voces acham ou pensam...


isto foi so para reafirmar a posição .. Ja que quando o Vitto_^^ postou o seu topico , ninguem achou nada;; Eu quis é enfatizar o que ele perguntou

Este post começou perguntando o que era melhor entre Halt, Close ou Application.Terminate.Não foi questionado sobre como terminar uma aplicação bruscamente.


eu que imaginei que o colega PauloSowfatare estava mencionado sobre : [b:49fd0ff014]qual o melhor método de se finalizar bruscamente um programa[/b:49fd0ff014].. E ainda continuo achando que esta era a sua idéia original...Se não for o caso de terminar bruscamente , acho que o[b:49fd0ff014] Rjun [/b:49fd0ff014]ja tinha respondido :

[b:49fd0ff014]Acompanhe os trechos inicais do diálogo:[/b:49fd0ff014] [b:49fd0ff014]Citação de Rjun [/b:49fd0ff014] [quote:49fd0ff014]Nenhuma. Use o Close do seu form principal.


como o PaullSoftware rebateu esta afirmação , como se pode ver a seguir :

[b:49fd0ff014]Citaçao de PaullSoftware[/b:49fd0ff014]
Como o Rjun escreveu: Nenhuma. Use o Close do seu form principal. simples assim... então pra que existem essas opções!


eu então que inicializei esta diferença :

Pera ai

[b:49fd0ff014]Citação de Marco salles[/b:49fd0ff014]
Uma coisa é finalizar a aplicação outra coisa e forçar com que a aplicação feche imediatamente...
[/quote:49fd0ff014]

e fim.........

É importante notar que ambas as API´s não respeitarão os destrutores dos objetos criados


mas foi isso que no seu tópico o Vitor_^^ descreveu :
[b:49fd0ff014]´[/b:49fd0ff014]Existe uma função da api do windows que termina um programa ou processo imediatamente, sem nenhum erro ou tela azul, que é o exitprocess(0); É o mais silencioso de todos, mas mantém a memória suja, porque não destroi ou libera nenhum objeto ou form. [b:49fd0ff014]´[/b:49fd0ff014]


A regra geral é que só devemos destruir o que foi criado por nós.


como regra sim..

Mesmo assim chamar Free apenas não vai interromper a execução da aplicação. Creio q deva apenas destruir os forms abertos.


eu não quis dizer isto.. Quis dizer que se voce estiver dentro do formPrincipal e quizer terminar bruscamente um programa , dentro daquilo que o vitor_^^ propos pode-se usar Application.free seguido de ExitProcess(0);

no mais é isso ai ..conhecer os métodos sua limitaçoes e aplica-los corretamente em cada situações..


GOSTEI 0
Rw Ltda

Rw Ltda

09/02/2006

procedure Halt ( { ExitValue : Integer } ) ;

Por Exemplo:
Halt(4);

The program terminates without running the ShowMessage statement. An error dialog is displayed:

Runtime error 4 at 0069FC94

Fonte: http://www.delphibasics.co.uk/RTL.asp?Name=Halt&ExpandCode1=Yes
GOSTEI 0
Bruno Guelere

Bruno Guelere

09/02/2006

Bom dia, há diferenças sim.

O Application.Terminate fecha a janela principal e dessa forma o aplicativo limpa a meméria. Halt() encerra abruptamente, e por isso, a memória não pode ser liberada, tabelas não são fechadas e assim por diante.
GOSTEI 1
Gerllanio Oliveira

Gerllanio Oliveira

09/02/2006

me ajudou pacas

Pera ai Uma coisa é finalizar a aplicação outra coisa e forçar com que a aplicação feche imediatamente...


desculpe , esta ultima colocaçao para o PaullSoftware

simples assim... então pra que existem essas opções!


e não tem relação com a resposta do cabelo

Com relação a resposta do cabelo

Se não me engano... A função Halt(); é utilizada para fechar TODOS os forms de um determinado nível, indicado pelo número que passamos como parâmetro... exemplo... se tiver 5 forms abertos... sendo 1 principal, outros 2 como filhos e mais dois como netos... se desejar fechar os forms do 3º nível, então dou um Halt(2).. E ASSIM POR DIANTE...


Acho que não procede isto.. :cry: :cry: :cry:


GOSTEI 0
Arthur Heinrich

Arthur Heinrich

09/02/2006

Uma aplicação que utiliza a classe Application geralmente registra o form principal e é executado o método Application.Run.

Neste método, é executado um loop para o tratamento de mensagens do Windows (Message Handler).

O loop termina quando o form principal é encerrado (Form.Close) ou quando a variável Application.Terminated se torna True, o que é feito com o Application.Terminate.

Nas duas situações, após sair do loop do Message Handler, a classe Application irá destruir todos os forms registrados, bem como os componentes que pertençam a cada um.

Lembrando que um componente pertence a outro, quando o Owner do componente indica o outro.

Um componente é visualizado dentro de outro quando o Parent aponta para o outro.

Se temos um componente cujo parent aponta para um form, mas o owner não aponta para o form, ao destruir o form, o componente não será destruído.

Independentemente de como a aplicação Delphi aloca a memória internamente, quando instancia uma classe, por exemplo, toda a memória é alocada de regiões de memória alocadas previamente do SO, que gerencia internamente a alocação, de forma mais simples e eficiente.

Ao executar o comando Halt(<error code>), entendo que estamos encerrando a aplicação diretamente. A classe Application não irá concluir o processo de finalização, os objetos instanciados não serão destruídos e eventuais conexões com bancos de dados e outras aplicações não serão encerradas corretamente.

Entretanto, ao encerrar o processo, o SO vai liberar a memória alocada pela aplicação, que contém todos os componentes alocados internamente.

Acredito que, mesmo utilizando a rotina Halt(), caso tenha sido definida uma rotina de encerramento, através da variável ExitProc, esta será chamada. Isto vem desde o Turbo Pascal, onde não existiam units com métodos initialization/finalization. A aplicação geralmente guardava o endereço de ExitProc antes de substituir seu valor, criando uma espécie de lista ligada de rotinas de encerramento. Ao ser chamada, a rotina executava o código de encerramento e restaurava o conteúdo anterior, para que todas as rotinas fossem executadas na sequência inversa.
GOSTEI 0
POSTAR