Preciso de um exemplo de Thread
Preciso executar uma consulta no banco de dados em 40 e 40 segundos, só que não posso usar o componente Timer, que é ruim para a performace, eu precisava usar um Thread, só que não tenho a mínima ideia de como usar... Se alguém puder me ajudar, me passando um exemplo detalhado de como usar esse procedimento.
Desde já Obrigado.
Urgente
Desde já Obrigado.
Urgente
Edusgouveia
Curtidas 0
Respostas
Maxwell_monteiro
20/08/2003
type
TMyThread = class(TThread)
procedure Execute; override;
end;
var
MyThread: MyThread;
TMyThread.Execute;
begin
// codigo a ser executado em uma linha de execução a parte (thread)
end;
é mais ou menos assim! pois não uso muito! mas o codigo que for colocado dentro do metodo execute será executado em uma linha de execução a parte ou seja uma thread!
TMyThread = class(TThread)
procedure Execute; override;
end;
var
MyThread: MyThread;
TMyThread.Execute;
begin
// codigo a ser executado em uma linha de execução a parte (thread)
end;
é mais ou menos assim! pois não uso muito! mas o codigo que for colocado dentro do metodo execute será executado em uma linha de execução a parte ou seja uma thread!
GOSTEI 0
Max_ribeiro
20/08/2003
Visite o site:
http://www.canaldelphi.cjb.net
Tem um artigo sobre Threads muito bom.
[]´s
_____________
Max_Ribeiro 8)
Canais #delphi interbase firebird IRC Brasnet
http://www.canaldelphi.cjb.net
Tem um artigo sobre Threads muito bom.
[]´s
_____________
Max_Ribeiro 8)
Canais #delphi interbase firebird IRC Brasnet
GOSTEI 0
Mturon
20/08/2003
Meu camarada, seu problema é exatamente igual ao meu. Preciso de uma informação atualizada na tela a cada 30s. Realmente o timer não presta para isso, pois enquanto a query não retorna, vc está travado. Se vc utilizar uma thread simples como o exemplo do Maxwel, tb não vai funcionar, pois uma aplicação para ser realmente multi-thread e executar duas consultas concorrentes no banco de dados, ela precisa ser tb multi-Session. Cada Session, abre uma conexção com o banco independente da outra, tornando assim realmente sua tela livre enquando a query e reaberta a cada x tempo. O problema é que eu ainda não consegui utilizar corretamente a Session juntamente com a thread. Este é o caminho, se vc conseguir ir mais adiante, por favor manda um email me explicando como (turon.cm@funcef.com.br), e se eu descobrir como, te envio a resposta.
GOSTEI 0
Beppe
20/08/2003
...só que não posso usar o componente Timer, que é ruim para a performace...
Porque pensa que um thread seria melhor que um timer? Não que não possa ser usado assim, mas um thread seria para outras ocasiões.
GOSTEI 0
Mturon
20/08/2003
Realmente a diferença, pelo menos visualmente é sutil. Porém utilizando thread em uma session separada consegui uma performance muito melhor, além de as queries do form rodarem concomitantemente com a query da thread e retornarem seus resultsets ao mesmo tempo, consumindo somente o tempo de abertura da query mais lenta. Não sei para vc mas para mim valeu a pena. Ficou melhor.
GOSTEI 0
Alesabino
20/08/2003
Realmente a diferença, pelo menos visualmente é sutil. Porém utilizando thread em uma session separada consegui uma performance muito melhor, além de as queries do form rodarem concomitantemente com a query da thread e retornarem seus resultsets ao mesmo tempo, consumindo somente o tempo de abertura da query mais lenta. Não sei para vc mas para mim valeu a pena. Ficou melhor.
Coloque aqui a sua solução para todos poderem aprender!!!!
GOSTEI 0
Lucas Silva
20/08/2003
Dê uma olhada neste tópico:
http://delphiforum.icft.com.br/forum/viewtopic.php?t=33539
[color=red:988e89aa71][b:988e89aa71]Atenção!![/b:988e89aa71][/color:988e89aa71] [b:988e89aa71]Editando o tópico.[/b:988e89aa71]
O link informado está quebrado devido a mudança no host do fórum. O tópico é este: [url=http://forum.clubedelphi.net/viewtopic.php?t=33539]http://forum.clubedelphi.net/viewtopic.php?t=33539[/url].
Sandra/Moderação
http://delphiforum.icft.com.br/forum/viewtopic.php?t=33539
[color=red:988e89aa71][b:988e89aa71]Atenção!![/b:988e89aa71][/color:988e89aa71] [b:988e89aa71]Editando o tópico.[/b:988e89aa71]
O link informado está quebrado devido a mudança no host do fórum. O tópico é este: [url=http://forum.clubedelphi.net/viewtopic.php?t=33539]http://forum.clubedelphi.net/viewtopic.php?t=33539[/url].
Sandra/Moderação
GOSTEI 0
Alesabino
20/08/2003
[quote:7344a56997=´Lucas Alves Silva´]Dê uma olhada neste tópico:
http://delphiforum.icft.com.br/forum/viewtopic.php?t=33539
[color=red:7344a56997][b:7344a56997]Atenção!![/b:7344a56997][/color:7344a56997] [b:7344a56997]Editando o tópico.[/b:7344a56997]
O link informado está quebrado devido a mudança no host do fórum. O tópico é este: [url=http://forum.clubedelphi.net/viewtopic.php?t=33539]http://forum.clubedelphi.net/viewtopic.php?t=33539[/url].
Sandra/Moderação[/quote:7344a56997]
Olá Lucas
Já li todo o tópico e não achei que tenha acrescentado muito.
Achei esse aqui mais promissor e resolvi respondê-lo.
Obrigado pela lembrança.
Alessandro.
http://delphiforum.icft.com.br/forum/viewtopic.php?t=33539
[color=red:7344a56997][b:7344a56997]Atenção!![/b:7344a56997][/color:7344a56997] [b:7344a56997]Editando o tópico.[/b:7344a56997]
O link informado está quebrado devido a mudança no host do fórum. O tópico é este: [url=http://forum.clubedelphi.net/viewtopic.php?t=33539]http://forum.clubedelphi.net/viewtopic.php?t=33539[/url].
Sandra/Moderação[/quote:7344a56997]
Olá Lucas
Já li todo o tópico e não achei que tenha acrescentado muito.
Achei esse aqui mais promissor e resolvi respondê-lo.
Obrigado pela lembrança.
Alessandro.
GOSTEI 0
Mturon
20/08/2003
A Solução que eu encontrei até que não é complicada.
Eu criei um novo datamodule, com um componente TDataBase e um TSession. Apontei a propriedade SessionName do DataBase para a Session criada. Coloquei então meu componente query e um datasource.
No create do datamodule utilizei estes comandos:
DataBase.Connected := False;
DataBase.Params := DataModuledoSistema.DataBasedoSistema.Params;
DataBase.Connected := True;
Deste modo criei uma nova conexão com o banco utilizando os mesmos dados da conexão atual.
Assim ficou minha declaração da Thread:
TThread = Class(TThread)
Private
I : Integer;
Painel: TPanel;
procedure AbreQry;
Protected
Procedure Execute; OverRide;
Public
Constructor CreateT(pnlDisp: TPanel);
Procedure Suspender;
Procedure Continuar;
End;
O método construtor ficou assim:
Constructor TThread.CreateT(pnlDisp: TPanel);
Begin
{ Executa Heranca Criando a Thread Suspença }
Inherited Create(True);
Priority := tpNormal;
FreeOnTerminate := True;
Painel := pnlDisp; // Painel do Form que chama a thread que recebe o
// Resultado da thread
{ Inicia a thread }
Suspended := False;
End;
O método execute:
Procedure TThread.Execute;
Begin
Synchronize(AbreQry);
Application.ProcessMessages;
if not OnLine then
Self.Suspend;
while not Terminated do
begin
Inc(I);
if I >= 90000000 then
begin
I := 1;
Synchronize(AbreQry);
end;
Application.ProcessMessages;
if (not OnLine) and (not Self.Suspended) then
Self.Suspend;
end;
End;
A rotina AbreQuery deve preencher os parametros, abrir e ao final, preencher o painel com o resultado pretendido:
procedure TThread.AbreQry;
begin
with FormqueChama, DataModuledaThread do
begin
Query.ParamByName(´X´).asInteger := 1;
Query.Open;
Painel.Caption := FormatFloat(´#,,,,0.00 ´,
Query.Campo.AsFloat);
end;
end;
No Form, criar uma variavel global deste modo:
var MyThread: TThread;
No evento FormShow:
MyThread := TThread.CreateT(PnlDisp);
Espero ter ajudado.
Marco Turon
Eu criei um novo datamodule, com um componente TDataBase e um TSession. Apontei a propriedade SessionName do DataBase para a Session criada. Coloquei então meu componente query e um datasource.
No create do datamodule utilizei estes comandos:
DataBase.Connected := False;
DataBase.Params := DataModuledoSistema.DataBasedoSistema.Params;
DataBase.Connected := True;
Deste modo criei uma nova conexão com o banco utilizando os mesmos dados da conexão atual.
Assim ficou minha declaração da Thread:
TThread = Class(TThread)
Private
I : Integer;
Painel: TPanel;
procedure AbreQry;
Protected
Procedure Execute; OverRide;
Public
Constructor CreateT(pnlDisp: TPanel);
Procedure Suspender;
Procedure Continuar;
End;
O método construtor ficou assim:
Constructor TThread.CreateT(pnlDisp: TPanel);
Begin
{ Executa Heranca Criando a Thread Suspença }
Inherited Create(True);
Priority := tpNormal;
FreeOnTerminate := True;
Painel := pnlDisp; // Painel do Form que chama a thread que recebe o
// Resultado da thread
{ Inicia a thread }
Suspended := False;
End;
O método execute:
Procedure TThread.Execute;
Begin
Synchronize(AbreQry);
Application.ProcessMessages;
if not OnLine then
Self.Suspend;
while not Terminated do
begin
Inc(I);
if I >= 90000000 then
begin
I := 1;
Synchronize(AbreQry);
end;
Application.ProcessMessages;
if (not OnLine) and (not Self.Suspended) then
Self.Suspend;
end;
End;
A rotina AbreQuery deve preencher os parametros, abrir e ao final, preencher o painel com o resultado pretendido:
procedure TThread.AbreQry;
begin
with FormqueChama, DataModuledaThread do
begin
Query.ParamByName(´X´).asInteger := 1;
Query.Open;
Painel.Caption := FormatFloat(´#,,,,0.00 ´,
Query.Campo.AsFloat);
end;
end;
No Form, criar uma variavel global deste modo:
var MyThread: TThread;
No evento FormShow:
MyThread := TThread.CreateT(PnlDisp);
Espero ter ajudado.
Marco Turon
GOSTEI 0
Marcosrocha
20/08/2003
Preciso de exemplos de Threads bem simples!!
Já postei no outro tópico mas aqui também diz sobre o assunto!!
Tipo como eu crio uma thread?
Queria um exemplo assim!!
Crio a thread e fecho minha aplicação. A thread vê q a aplicação foi fechada e abre ela novamente e se ´auto destroi´... 8)
Já postei no outro tópico mas aqui também diz sobre o assunto!!
Tipo como eu crio uma thread?
Queria um exemplo assim!!
Crio a thread e fecho minha aplicação. A thread vê q a aplicação foi fechada e abre ela novamente e se ´auto destroi´... 8)
GOSTEI 0
Asensio
20/08/2003
Preciso executar uma consulta no banco de dados em 40 e 40 segundos, só que não posso usar o componente Timer, que é ruim para a performace, eu precisava usar um Thread, só que não tenho a mínima ideia de como usar... Se alguém puder me ajudar, me passando um exemplo detalhado de como usar esse procedimento.
Desde já Obrigado.
Urgente
Eduardo,
Pq usar a Thread em vez do TTimer se o TTimer é uma Thread também. O TTimer move um novo ponteiro no sistema mesmo o fluxo dele esteja em outra parte. Por isso muita gente acaba se atrapalhando em usa-lo.
A performace depende de como usa-lo. Se não souber desligar ele no momento correto, vc estará executando diversos ponteiros no seu sistema e se ainda estiver usando consulta em banco de dados com certeza irá ter uma grande perda de performace. Mas no exemplo que vc deu dá para se trabalhar perfeitamente com ele.
Fui
GOSTEI 0
Beppe
20/08/2003
Oi!
Isto é incorreto. Um timer nem de longe se parece com um thread. O sistema indica que o temporizador esgotou enviando uma mensagem.
O timer só envia uma nova mensagem assim que a mensagem anterior for recebida, deste modo, mensagens pode não ser enviadas caso a responsividade seja lenta.
Pq usar a Thread em vez do TTimer se o TTimer é uma Thread também. O TTimer move um novo ponteiro no sistema mesmo o fluxo dele esteja em outra parte. Por isso muita gente acaba se atrapalhando em usa-lo.
Isto é incorreto. Um timer nem de longe se parece com um thread. O sistema indica que o temporizador esgotou enviando uma mensagem.
A performace depende de como usa-lo. Se não souber desligar ele no momento correto, vc estará executando diversos ponteiros no seu sistema e se ainda estiver usando consulta em banco de dados com certeza irá ter uma grande perda de performace. Mas no exemplo que vc deu dá para se trabalhar perfeitamente com ele.
O timer só envia uma nova mensagem assim que a mensagem anterior for recebida, deste modo, mensagens pode não ser enviadas caso a responsividade seja lenta.
GOSTEI 0
Lucaniasalvatore
20/08/2003
Bom dia, Eduardo.
Segue abaixo um exemplo básico de tarefa.
----------Código------------------
unit UThread1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type T1 = class(TThread)
private
I:integer;
procedure Mostra;
protected
procedure Execute; override;
end; { of class declaration }
type T2 = class(TThread)
private
I:integer;
procedure Execute; override;
procedure Mostra;
end; { of class declaration }
type
TForm1 = class(TForm)
Label1: TLabel;
Label2: TLabel;
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure T1.Mostra;
begin
Form1.Label1.Caption:=IntToStr(I);
end;
procedure T1.Execute;
var LI:integer;
begin
for LI:=1 to 3000 do
begin
I:=LI;
Synchronize(Mostra);
end;
end; { of procedure }
procedure T2.Mostra;
begin
Form1.Label2.Caption:=IntToStr(I);
end;
procedure T2.Execute;
var LI:integer;
begin
for LI:=1 to 6000 do
begin
I:=LI;
Synchronize(Mostra);
end;
end; { of procedure }
procedure TForm1.Button1Click(Sender: TObject);
begin
T1.Create(false);
T2.Create(false);
end; { of procedure }
end.
---------------------fim do código-----------
Creio que uma vez mapeada a forma de criar a tarefa, vc conseguirá adaptar suas funções e procedimentos.
Boa programação,
Lucania Salvatore
Segue abaixo um exemplo básico de tarefa.
----------Código------------------
unit UThread1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type T1 = class(TThread)
private
I:integer;
procedure Mostra;
protected
procedure Execute; override;
end; { of class declaration }
type T2 = class(TThread)
private
I:integer;
procedure Execute; override;
procedure Mostra;
end; { of class declaration }
type
TForm1 = class(TForm)
Label1: TLabel;
Label2: TLabel;
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure T1.Mostra;
begin
Form1.Label1.Caption:=IntToStr(I);
end;
procedure T1.Execute;
var LI:integer;
begin
for LI:=1 to 3000 do
begin
I:=LI;
Synchronize(Mostra);
end;
end; { of procedure }
procedure T2.Mostra;
begin
Form1.Label2.Caption:=IntToStr(I);
end;
procedure T2.Execute;
var LI:integer;
begin
for LI:=1 to 6000 do
begin
I:=LI;
Synchronize(Mostra);
end;
end; { of procedure }
procedure TForm1.Button1Click(Sender: TObject);
begin
T1.Create(false);
T2.Create(false);
end; { of procedure }
end.
---------------------fim do código-----------
Creio que uma vez mapeada a forma de criar a tarefa, vc conseguirá adaptar suas funções e procedimentos.
Boa programação,
Lucania Salvatore
GOSTEI 0