Ir para conteúdo
Fórum Script Brasil
  • 0

While


s3c

Pergunta

Posts Recomendados

  • 0

Forma de usar:

procedure.....

var valor:real;

begin

with nomedatabelaouconsulta, label1 do begin

first;

while not eof do begin

valor := valor + Fieldbyname('nomedocampo').asfloat;

next;

end;

caption := formatfloat('###,##0.00',valor);

end;

end;

//Tradução: enquanto não for o fim da tabela faça: soma os valores do campo.

//voce tem que colocar o first no antes do loop pois indica onde tudo vai comecar o eof significa endoffile final do arquivo ou seja enquanto não chegar o final do arquivo faça. e o next pula de registro a registro. mangou. no with atribui-se propriedades a varios componentes contanto que sejam de tipos diferentes.

falows manow...

____________________________________

Eder Moraes

Link para o comentário
Compartilhar em outros sites

  • 0

Forma de usar:

procedure.....

var valor:real;

begin

with nomedatabelaouconsulta, label1 do begin

first;

while not eof do begin

valor := valor + Fieldbyname('nomedocampo').asfloat;

next;

end;

caption := formatfloat('###,##0.00',valor);

end;

end;

//Tradução: enquanto não for o fim da tabela faça: soma os valores do campo.

//voce tem que colocar o first no antes do loop pois indica onde tudo vai comecar o eof significa endoffile final do arquivo ou seja enquanto não chegar o final do arquivo faça. e o next pula de registro a registro. mangou. no with atribui-se propriedades a varios componentes contanto que sejam de tipos diferentes.

falows manow...

____________________________________

Eder Moraes

Primeiro post:

Porque ele satisfaz a condição ? Que true é esse ?
Link para o comentário
Compartilhar em outros sites

  • 0

Opa

isso aí é quando é preciso testar a condição no meio do loop, e não no começo, exemplo ->

Function _search(brd: TBoard; depth : byte) : TMove;
var
  node : array of byte;//Aponta para a jodada de uma resposta na qual estamos
  PList : array of TMoves;//Guarda as jogadas que serão feitas para cada resposta
  ply{A resposta em que estamos}, i : byte;
  Color : TTurn;
  score : array of longint;
  //MateCheck : TMoves;
  Res : byte;
begin
  Color:=Brd.Turn;
  if (depth < 2) then depth:=2;
  if (depth > 8) then depth:=8;
  SetLength(node, depth+1);
  SetLength(PList, depth+1);
  for i:=1 to depth do node[i]:=1;
  ply:=1;
  Brd.WriteMoves(PList[1]);
  if (Plist[1].Length = 0) then exit;
  setlength(score,Plist[1].length+1);
  for i:=1 to Plist[1].Length do
  begin
    score[i]:=0;
    Brd.MakeMove(PList[1].m[i]);
    //Brd.WriteMoves(MateCheck);
    if (Brd.Mate) and Brd.Xeque(não(clr(color),peao)) then
    begin
      _Search:=PList[1].m[i];
      exit;
    end;
    Brd.TakeBack(PList[1].m[i]);
  end;
  //*Repetição principal*//
  while true do begin
    if (ply < depth) then
    begin
      if (node[ply] <= PList[ply].Length) then
      begin
        {Faz a jogada e vai mais fundo}
        Brd.MakeMove(PList[ply].m[node[ply]]);
        if (brd.Turn = color) then
          dec(score[node[1]],KindVal(PList[ply].m[node[ply]].Tipo)) else
          inc(score[node[1]],KindVal(PList[ply].m[node[ply]].Tipo));
        //inc(node[ply]);
        inc(ply);
        Brd.WriteMoves(Plist[ply]);
        if (PList[ply].Length = 0) then
        begin
          if (brd.Turn = color) then
            dec(score[node[1]],(160 div ply)) else
            inc(score[node[1]],(160 div ply));
          node[ply]:=1;
          dec(ply);
          inc(node[ply]);//*****//
          Brd.TakeBack(PList[ply].m[pred(node[ply])]);
        end;
      end else
      begin
        if (ply <= 1) then break;
        node[ply]:=1;
        dec(ply);
        inc(node[ply]);//*****//
        Brd.TakeBack(PList[ply].m[pred(node[ply])]);
      end;
    end else if (ply = depth) then
    begin
      if (node[ply] <= PList[ply].Length) then
      begin
        Brd.MakeMove(PList[ply].m[node[ply]]);
        //Brd.WriteMoves(MateCheck);
        if (Brd.Mate) then
        begin
          if (brd.Turn = color) then
            dec(score[node[1]],(160 div ply)) else
            inc(score[node[1]],(160 div ply));
        end;
        if (brd.Turn = color) then
          dec(score[node[1]],KindVal(PList[ply].m[node[ply]].Tipo)) else
          inc(score[node[1]],KindVal(PList[ply].m[node[ply]].Tipo));
        Brd.TakeBack(PList[ply].m[node[ply]]);
        Inc(node[ply]);
      end else
      begin
        node[ply]:=1;
        dec(ply);
        inc(node[ply]);//******//
        Brd.TakeBack(PList[ply].m[pred(node[ply])]);
      end;
    end;
  end;
  //*Fim da repetição pricipal*//
  res:=1;
  for i:=1 to pred(length(score)) do
  begin
    if (score[i] > score[res]) then
    res:=i;
  end;
  _Search:=PList[1].m[res];
end;
Isso aí eu tirei de um código de um programa meu, aí você testa a condição no meio do loop e sai do loop com o comando break->
if (x > y) then break;

Abraço.

Link para o comentário
Compartilhar em outros sites

  • 0

Bom, o exit sai do procedimento todo, e o break sai só do loop.

Ora bolas, o while repete o loop enquanto a condição for True, não é mesmo? Tipo se (x > y) for True ele roda o bloco de repetição, senão ele pula o bloco e continua executando o código abaixo. Então se você quiser que essa condição seja sempre True é só você colocar a constante booleana True, você não acha?

porque aí ele vai chegar lá e vai testar a condição para ver o seu valor, e qual vai ser o valor: True.

Entendeu?

Mesma coisa que

repeat
.
.
.
.
.
until false;

Porque no repeat ele só não volta pro inicio do loop se a condição for verdadeira, se for falsa ele volta. ;)

Link para o comentário
Compartilhar em outros sites

  • 0

True = Verdadeiro...

Então

while true do begin
  // Tarefas... tarefas... tarefas...
  // Quando quiser interromper o "loop", é só dar Break!
End;
Isto é perfeitamente válido... no meu tempo de MWBasic:
Rem -1 = True
ok = -1
While ok 
  Write "Vou ficar repetindo isto toda vida, até alguém colocar ok=0"
Wend
o que seria o mesmo que fazer:
Rem -1 = True
ok = -1
While ok = (-1)
  Write "Vou ficar repetindo isto toda vida, até alguém colocar ok=0"
Wend
ou
Rem -1 = True
ok = -1
While not (ok = 0)
  Print "Vou ficar repetindo isto toda vida, até alguém colocar ok=0"
Wend

E para quê fazer um loop "sem condição" ou "condição infinita"?

Tenho programas que "rodam" como serviços (é... dá para transformar seus aplicativos Delphi em serviços executados nos WinXP, NT, 2000, 2003..., no mínimo a partir do Delphi6 - o que eu uso) e estes programas funcionam em um loop infinito...

Como exemplo, tenho um validador de inscrição estadual que atende a programas antigos em Clipper - rodando em 386's, 486's, etc..., conectados a um servidor (XP) e que precisam verificar se uma I.E. é válida, enviando a requisição desta consulta pela rede, diretamente ao "serviço" sendo executado no servidor.

Como a DLL de validação fornecida pela SEF-RS não roda sob Win311 ou MsDOS, precisei criar este serviço para isso...

Link para o comentário
Compartilhar em outros sites

  • 0

Putz, ainda não entendeu. 3º tentativa ->

O compilador requer uma expressão, variável ou constante booleana depois do while. Então se for variável vai ficar assim ->

Var 
  cansado : boolean;
begin
  while cansado do 
  begin
    sleep;
    cansado:=(sono > disposição);
  end;
end;
se for constante, ora quais constantes booleanas, False e True. ->
type
  Boolean = (false, true); //A declaração é interna do compilador e fica como se estivesse declarada no início da unit System
begin
  while true do ...;
end;
Se for expressão booleana tipo (x > y) então o compilador vai ter que avaliar ele para ver se o valor é igual a constante True ou igual a constante False. Vamos ver um exemplo no assembly. Primeiro o compilador se depara com alguma coisa que tem que ver se é expressão ou constante/variável. Se for a expressão (x > y) por exemplo ele vai fazer->
{Tira os valores da pilha}
POP EAX
POP EDX
{Compara os valores}
TEST EAX, EDX
{pula se for maior}
JG maior
{valor se falso}
MOV BX, 0
JUMP teste
maior:
MOV BX, 1
teste:
TEST BX, 0
JG comandosSeVerdadeiro
JUMP comandosSeFalso 
Foi necessário testar os 2 valores para colocar o resultado em BX, no caso de ele encontrar variável ou constante ele teria apenas que puxar o seu valor da pilha e executar o último teste ->
XOR BX, BX
POP BL
teste:
TEST BX, 0
JG comandosSeVerdadeiro
JUMP comandosSeFalso 

Entendeu mais ou menos?

Link para o comentário
Compartilhar em outros sites

  • 0

Help do Delphi:

A while statement is similar to a repeat statement, except that the control condition is evaluated before the first execution of the statement sequence. Hence, if the condition is false, the statement sequence is never executed.

The syntax of a while statement is

while expression do statement

where expression returns a Boolean value and statement can be a compound statement. The while statement executes its constituent statement repeatedly, testing expression before each iteration. As long as expression returns True, execution continues.

Então: While true do; para mim true seria o retorno booleano da avaliação de uma expressão que neste caso não existe.

Link para o comentário
Compartilhar em outros sites

  • 0

Realmente s3c, faz sentido o seu questionamento (caiu a ficha) :)

Mas acho que nem mesmo o "dono dos porcos" consegue entender essas coisas, São tantas funçoes, procedimentes, etc, etc, ect..., que algumas acabam se atropelando (bug) se é que podemos chamar isso de bug, acho que não. né???

levando em consideração que eu comentei num post anterior, estaria executando como se fosse um IF, se True entra no loop, se False não entra. :huh:

Abs. Progr'amador.

;)

Link para o comentário
Compartilhar em outros sites

  • 0

Beleza,

Vamos supor ->

var
  x, y: integer;
begin
  x:=200;
  y:=20;
  while true do y:=y+3;
  Caption:=inttostr(x)+inttostr(y);
end;
Seja com o While true ou While (0=0) o compilador faz sempre isso->
0045325C EBFE             jmp $0045325c
Ou seja, ele nem chega a incrementar y porque ele sabe que não tem condição para sair do loop então ele fica em uma linha que tem um JUMP incondicional para a mesma linha. Agora se for assim ->
var
  x, y : integer;
begin
  x:=200;
  y:=10;
  while true do begin y:=y+3; if (y>40000) then break; end;
  Caption:=inttostr(y)+inttostr(x);
end;
O compilador vai fazer isso ->
00453268 83C303           add ebx,$03
0045326B 81FB409C0000     cmp ebx,$00009c40
00453271 7EF5             jle $00453268
Ou seja, ele ignora totalmente o teste do true porque ele sabe que a única condição para ele sair é o teste do break, então a única coisa que ele testa é a condição para break. Agora se for assim ->
var
  x, y : integer;
begin
  x:=200;
  y:=10;
  while true do begin y:=y+3; if false then break; end;
  Caption:=inttostr(y)+inttostr(x);
end;
O compilador vai fazer isso ->
00453268 83C303           add ebx,$03
0045326B EBFB             jmp $00453268
ou seja, ele chega a incrementar y mas não testa nada porque mais uma vez ele sabe que não existe condição para sair do loop. Nesse caso o compilador ignora completamente o trecho if false then break; por que ele sabe que nunca será executado um comando precedido por if false, então não é gerado código para isso. Agora se for assim ->
var
  x, y : integer;
begin
  x:=200;
  y:=10;
  while (x > y) do dec(x);
  Caption:=inttostr(y)+inttostr(x);
end;
O compilador vai fazer isso ->
Unit1.pas.33: while (x > y) do dec(x);
00453268 3BF3             cmp esi,ebx
0045326A 7D05             jnl $00453271
0045326C 4B               dec ebx
0045326D 3BF3             cmp esi,ebx
0045326F 7CFB             jl $0045326c

Ou seja, em tempo de compilação o compilador verificou que para ser avaliada essa expressão seria necessário comparar os registradores ESI e EBX e usar o JUMP condicional JL para fazer o loop.

Entendeu agora?

Link para o comentário
Compartilhar em outros sites

  • 0

Beleza,

Vamos supor ->

var
  x, y: integer;
begin
  x:=200;
  y:=20;
  while true do y:=y+3;
  Caption:=inttostr(x)+inttostr(y);
end;
Seja com o While true ou While (0=0) o compilador faz sempre isso->
0045325C EBFE             jmp $0045325c

Ou seja, ele nem chega a incrementar y porque ele sabe que não tem condição para sair do loop então ele fica em uma linha que tem um JUMP incondicional para a mesma linha.

Ele nem chega a incrementar y?

Você tem certeza ? Acho que não; ele fica incrementando y continuamente. Coloque um break-point e veja.

Outra coisa, se ele sabe que está em loop infinito, porque não é dada ao menos uma msg de warning ?

Link para o comentário
Compartilhar em outros sites

  • 0

While not(s3c.Understand) and (Self.Alive) do
try
  Explain(s3c);
except Kill(Self);
end;

Ele nem chega a incrementar y?

Você tem certeza ? Acho que não; ele fica incrementando y continuamente. Coloque um break-point e veja.

Foi exatamente adicionando um break point que eu ví. Ele não incrementa y porque sabe que não teria sentido já que o programa não vai mais a lugar nenhum depois dali. Veja você mesmo, adicione um break point.

Outra coisa, se ele sabe que está em loop infinito, porque não é dada ao menos uma msg de warning ?
Acredito que seja porque loops infinitos são comuns dependendo do efeito esperado pelo programador, ou porque esqueceram de colocar mesmo.
Link para o comentário
Compartilhar em outros sites

  • 0
Veja se o caption do botão muda.

Não preciso nem ver, nesse caso é claro que vai mudar. Só não é modificado y quando seu valor não é usado posteriormente, ou seja, quando ocorre o warning "Value assigned to 'y' never used".

Link para o comentário
Compartilhar em outros sites

  • 0
Não preciso nem ver, nesse caso é claro que vai mudar. Só não é modificado y quando seu valor não é usado posteriormente, ou seja, quando ocorre o warning "Value assigned to 'y' never used".
É mesmo ?

Então deixe somente a linha do Inc(i), coloque um brak-point lá e veja se ele não incrementa.

Comigo no D6 e Turbo Delphi ele incrementa. Acho que nesses dois Delphis o compilador não sabe que está em loop infinito e talvez seja por isso que não dá nem um warning.

Link para o comentário
Compartilhar em outros sites

  • 0

Na 1º tentativa o computador travou nas 4. Na 2º tentativa o break point mostrou só uma linha ->

00453244 EBFE             jmp TForm1.Button1Click

Ou seja, como o valor de i não é usado ele desconsidera a linha, e como o while vem depois disso ele pula pro início do procedimento, ou seja, mesma linha. Conclusão no Delphi 2006 ele não incrementa mesmo o i.

Link para o comentário
Compartilhar em outros sites

  • 0

Curioso... aqui no Delphi6 e no Delphi4 não tenho erro nenhum...

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Buttons;

type
  TForm1 = class(TForm)
    Button1: TButton;
    StaticText1: TStaticText;
    BitBtn1: TBitBtn;
    StaticText2: TStaticText;
    procedure Button1Click(Sender: TObject);
    procedure BitBtn1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

Procedure TForm1.Button1Click(Sender: TObject);
Var
  iContador: Integer;
Begin
  StaticText1.Caption := 'algarismos: ';
  iContador := 1;
  while true do begin
    StaticText1.Caption := StaticText1.Caption+IntToStr(iContador)+' ';
    Inc(iContador);
    If iContador=11 then
      Break;
    {EndIf iContador=11}
  End;{while true}
End;

Procedure TForm1.BitBtn1Click(Sender: TObject);
Var
  x, y: integer;
Begin
  x:=200;
  y:=2147483000;
  while true do begin
    y:=y+3;
    StaticText2.Caption := 'y='+IntToStr(y)+' e '+
                           'x='+IntToStr(x)+'!';
    Application.ProcessMessages;
    Sleep(0025);
  End;{while true}
End;

End.

Estranho esse seu compilador...

Link para o comentário
Compartilhar em outros sites

  • 0

Curioso... aqui no Delphi6 e no Delphi4 não tenho erro nenhum...

Quem falou em erro. Ninguém disse que tem erro nenhum. Por que você postou essa mensagem? O que você quis dizer com esse código?

Link para o comentário
Compartilhar em outros sites

  • 0
Acho que é porque você disse que o computador travou.
Travou porque de vez em quando deve escapolir alguma coisa lá que trava mesmo, mas foi só uma vez, as outras vezes funcionou direitinho.

E a que conclusão chegamos, o registrador incrementa ou não?

Aqui se eu botar um break point no inc(i) ele nunca chega a brekar porque o i nunca incrementa, e se eu colocar um break point no while ele mostra somente um jump para o inicio do procedimento ->

00453244 EBFE             jmp TForm1.Button1Click
No Delphi 6 aconteceu a mesma coisa. Repare que se você colocar um procedimento assim->
procedure algo;
var
  a, b, c, d, e, f : cardinal;
begin
  a:=10;
  b:=20;
  c:=30;
  d:=40;
  e:=50;
  f:=50;
end;

Ele nem chega a alocar essas variáveis na pilha, quanto mais colocar um valor nelas. E nem chega a chamar o procedimento. Isso porque o compilador percebe que os valores não são usados nem as variáveis então ele elimina o código.

Link para o comentário
Compartilhar em outros sites

Participe da discussão

Você pode postar agora e se registrar depois. Se você já tem uma conta, acesse agora para postar com sua conta.

Visitante
Responder esta pergunta...

×   Você colou conteúdo com formatação.   Remover formatação

  Apenas 75 emoticons são permitidos.

×   Seu link foi incorporado automaticamente.   Exibir como um link em vez disso

×   Seu conteúdo anterior foi restaurado.   Limpar Editor

×   Você não pode colar imagens diretamente. Carregar ou inserir imagens do URL.



  • Estatísticas dos Fóruns

    • Tópicos
      152,3k
    • Posts
      652,3k
×
×
  • Criar Novo...