Problema com data no Select?

Delphi

02/11/2008

Pessoal tenho uma tabela assim
1 13 3 03.11.2008 V V V V 2 13 2 05.11.2008 V V 4 13 2 07.11.2008 V V 14 13 2 04.11.2008 V 15 13 3 05.11.2008 V 18 13 2 06.11.2008 V V V V 25 13 3 01.11.2008 V V V V V V 1 01/11/2008 23:37:42


Cada ´V´ deste ai fica em uma coluna

então montei uma select para trazer o count de cada coluna
select distinct(a.idcaixa),
       b.nmcaixa,
   ( select count(vdnaofinalizada)
     from movimento
     where b.idcaixa = idcaixa
       and vdnaofinalizada  = ´V´ )as vdnaofinalizado,

   ( select count(cxnaoinformado)
     from movimento
     where b.idcaixa = idcaixa
       and cxnaoinformado  = ´V´ )as CxNaoInformado,

   ( select count(inversaopgto)
     from movimento
     where b.idcaixa = idcaixa
       and inversaopgto  = ´V´ )as InversaoPgto,

   ( select count(vdfinaldeumdiapoutro)
     from movimento
     where b.idcaixa = idcaixa
       and vdfinaldeumdiapoutro  = ´V´ )as vdfinaldeumdiapoutro,

   ( select count(cxinfemdterrada)
     from movimento
     where b.idcaixa = idcaixa
       and cxinfemdterrada  = ´V´ )as cxinfemdterrada,

   ( select count(vlinformadocorretamente)
     from movimento
     where b.idcaixa = idcaixa
       and vlinformadocorretamente  = ´V´ )as vlinformadocorretamente

from
   movimento a, respcaixa b
where b.idcaixa = a.idcaixa
--and a.idcaixa = :varID
--and a.dtmovimento >= ´01/11/2008´ and a.dtmovimento <= ´01/11/2008´
--between :pdtIn and :pdtFn
     and a.cxnaoinformado  = ´V´

o resultado é este do select
2 teste2cc mns 3 1 0 2 1 2 3 mn 1 3 1 2 2 2 1 01/11/2008 23:43:26


Mais por exemplo se eu colocar esta linha aqui
[b:e929ec48b0]--and a.dtmovimento >= ´01/11/2008´ and a.dtmovimento <= [/b:e929ec48b0]´01/11/2008´
ou usar o between
[b:e929ec48b0]--between :pdtIn and :pdtFn
[/b:e929ec48b0]

Com data de 01/11/2008 a 01/11/2008, não esta me trazendo o resultado correto

que seria
3 mn 1 1 1 1 1 1 1


e não
3 mn 1 3 1 2 2 2 1


Ou seja ele esta pegando a ID certa que tem no dia 01/11/2008, mais esta somando tudo e não só o que esta naquela coluna.

Então pessoal, como faço para contar os valores corretos cfe. a data?

Obs: Estou usando Firebird 2.0 e ainda não testei no projeto, estou testando diretamente no IBExpert


Adriano_servitec

Adriano_servitec

Curtidas 0

Respostas

Adriano_servitec

Adriano_servitec

02/11/2008

Mesma coisa no aplicativo, ainda não deu certo, achei que poderia ser conversão de datas, mais não é
var
  DataIn, DataFn : TDate;
begin
  inherited;
  {Passando as datas para variaveis}
  DataIn := StrToDate(MaskEdit1.Text);
  DataFn := StrToDate(MaskEdit2.Text);
  with IBQListCaixa do
  begin
    Close;
    Sql.Clear;
    Sql.Text := ´ select distinct(a.idcaixa), b.nmcaixa, ´+
                ´ ( select count(vdnaofinalizada) ´ +
                ´ from movimento ´+
                ´ where b.idcaixa = idcaixa and vdnaofinalizada  = ´´V´´ )as vdnaofinalizado, ´ +
                ´ ( select count(cxnaoinformado) ´+
                ´ from movimento ´+
                ´ where b.idcaixa = idcaixa ´ +
                ´ and cxnaoinformado  = ´´V´´ )as CxNaoInformado, ´+
                ´ ( select count(inversaopgto) ´ +
                ´ from movimento ´+
                ´ where b.idcaixa = idcaixa and inversaopgto  = ´´V´´ )as InversaoPgto, ´ +
                ´ ( select count(vdfinaldeumdiapoutro) ´+
                ´ from movimento where b.idcaixa = idcaixa ´ +
                ´ and vdfinaldeumdiapoutro  = ´´V´´ )as vdfinaldeumdiapoutro, ´ +
                ´ ( select count(cxinfemdterrada) ´+
                ´ from movimento where b.idcaixa = idcaixa ´ +
                ´ and cxinfemdterrada  = ´´V´´ )as cxinfemdterrada, ´ +
                ´ ( select count(vlinformadocorretamente) ´+
                ´ from movimento where b.idcaixa = idcaixa ´ +
                ´ and vlinformadocorretamente  = ´´V´´ )as vlinformadocorretamente ´ +
                ´ from  movimento a, respcaixa b ´+
                ´ where b.idcaixa = a.idcaixa ´ +
                ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
                ´ and a.cxnaoinformado  = ´´V´´ ´;   
    ParamByName(´pdtIn´).asDate := DataIn;
    ParamByName(´pdtFn´).AsDate := DataFn;
    Open;
  end; 


Creio que esteja errado o select


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

02/11/2008

esta nova condicao por data não deveria estar em todos os subselects?


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

02/11/2008

não sei se entendi completamente sua necessidade, mas acredito que você pode deixar de utilizar todos esses subselects (que degradam a performance) e utilizar a função [i:605e84ac20]case[/i:605e84ac20] em conjunto com [i:605e84ac20]group by[/i:605e84ac20].
Sql.Text := ´ select a.idcaixa, b.nmcaixa, ´+
            ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as vdnaofinalizado, ´+
            ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as CxNaoInformado, ´+
            ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as InversaoPgto, ´ +
            ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as vdfinaldeumdiapoutro, ´ +
            ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as cxinfemdterrada, ´ +
            ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as as vlinformadocorretamente ´ +
            ´ from  movimento a, respcaixa b ´+
            ´ where b.idcaixa = a.idcaixa ´ +
            ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
            ´ and a.cxnaoinformado  = ´´V´´ ´+
            ´ group by a.idcaixa, b.nmcaixa ´;



GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

não sei se entendi completamente sua necessidade, mas acredito que você pode deixar de utilizar todos esses subselects (que degradam a performance) e utilizar a função [i:5577551814]case[/i:5577551814] em conjunto com [i:5577551814]group by[/i:5577551814].
Sql.Text := ´ select a.idcaixa, b.nmcaixa, ´+
            ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as vdnaofinalizado, ´+
            ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as CxNaoInformado, ´+
            ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as InversaoPgto, ´ +
            ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as vdfinaldeumdiapoutro, ´ +
            ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as cxinfemdterrada, ´ +
            ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
            ´          then 1 ´+
            ´          else 0 end) as as vlinformadocorretamente ´ +
            ´ from  movimento a, respcaixa b ´+
            ´ where b.idcaixa = a.idcaixa ´ +
            ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
            ´ and a.cxnaoinformado  = ´´V´´ ´+
            ´ group by a.idcaixa, b.nmcaixa ´;


Olá [b:5577551814]emerson.en[/b:5577551814], testei este select que você postou, pareçe que esta mostrando o resultado certo, não testei bem ainda.

Vou tentar mostrar como esta na tabela (vou encurtar os campos somente para mostrar como esta)

ID----data---------campo1----campo2-----campo3-----campo4
2-----01.11.2008-----V---------------------------------------------
2-----01.11.2008-----V-----------V-------------------------V-----


Então o select creio eu que não vai precisar desta condição aqui em destaque abaixo

´ from movimento a, respcaixa b ´+ ´ where b.idcaixa = a.idcaixa ´ + ´ and a.dtmovimento between :pdtIn and :pdtFn ´+ [color=blue:5577551814][i:5577551814]-- ´ and a.cxnaoinformado = ´´V´´ ´+[/i:5577551814][/color:5577551814] ´ group by a.idcaixa, b.nmcaixa ´;


Vou fazer mais uns testes, pra ver se esta correto os valores, mais a principio pareçe que sim.

Outra duvida também amigo.
mas acredito que você pode deixar de utilizar todos esses subselects (que degradam a performance) e utilizar a função case em conjunto com group by.

Aqui o que você quis dizer é que com os subselects ficaria mais lento o SQL?

Obrigado por me ajudar amigo.


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Ola Emerson, vendo aqui nos testes percebi que esta agrupando por ID, e eu preciso que cada dia tenha o seu resultado

ID----data---------campo1----campo2-----campo3-----campo4 2-----01.11.2008-----V--------------------------------------------- 2-----02.11.2008-----V-----------V-------------------------V-----


Então são datas diferente e mesmo assim agrupa num só sele


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

02/11/2008

selecione a data e a coloque no group by também.


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

selecione a data e a coloque no group by também.
Verdade, nem tinha pensado nisso. Agora pareçe que está certo.

Mais uma vez obrigado.


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Surgiu mais um problema, preciso montar o select dos responsaveis pelo caixa que mais erram em ordem dos que mais erram do maior para o menor.

Pensei num order by DESC, mais como seria neste select?

var
  DataIn, DataFn : TDate;
begin
  inherited;
  if RadioButton2.Checked = True then
  begin
    {Passando as datas para variaveis}
    DataIn := StrToDate(MaskEdit1.Text);
    DataFn := StrToDate(MaskEdit2.Text);
    with IBQListCaixa do
    begin
      Close;
      Sql.Clear;
      Sql.Text := ´ select a.idcaixa, b.nmcaixa, c.nmloja, ´+
                  ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdnaofinalizado, ´+
                  ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as CxNaoInformado, ´+
                  ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as InversaoPgto, ´ +
                  ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdfinaldeumdiapoutro, ´ +
                  ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as cxinfemdterrada, ´ +
                  ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vlinformadocorretamente, ´ +
                   ´ sum(case when coalesce(a.sangriaincorreta,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as sangriaincorreta, ´ +
                  ´ sum(case when coalesce(a.outrostperros,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as outrostperros ´ +
                  ´ from  movimento a, respcaixa b, lojas c ´+
                  ´ where b.idcaixa = a.idcaixa ´ +
                  ´ and c.id_loja = b.idloja ´+
                  ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
                  ´ group by a.idcaixa, b.nmcaixa, c.nmloja ´;//+
//                  ´ order by vdnaofinalizada,  desc ´;
      ParamByName(´pdtIn´).asDate := DataIn;
      ParamByName(´pdtFn´).AsDate := DataFn;
      Open;
    end;


Não estou sabendo como montar este SQL

Grato pela ajuda
Adriano.


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

02/11/2008

e como você identifica quem errou mais? apenas por um campo ou a soma desses campos?


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

e como você identifica quem errou mais? apenas por um campo ou a soma desses campos?
Eu acho que tem que ser a soma de todos os campos, pois fiz assim e não deu certo

var
  DataIn, DataFn : TDate;
begin
  inherited;
  if RadioButton2.Checked = True then
  begin
    {Passando as datas para variaveis}
    DataIn := StrToDate(MaskEdit1.Text);
    DataFn := StrToDate(MaskEdit2.Text);
    with IBQListCaixa do
    begin
      Close;
      Sql.Clear;
      Sql.Text := ´ select a.idcaixa, b.nmcaixa, c.nmloja, ´+
                  ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdnaofinalizado, ´+
                  ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as CxNaoInformado, ´+
                  ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as InversaoPgto, ´ +
                  ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdfinaldeumdiapoutro, ´ +
                  ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as cxinfemdterrada, ´ +
                  ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vlinformadocorretamente, ´ +
                  ´ sum(case when coalesce(a.sangriaincorreta,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as sangriaincorreta, ´ +
                  ´ sum(case when coalesce(a.outrostperros,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as outrostperros ´ +
                  ´ from  movimento a, respcaixa b, lojas c ´+
                  ´ where b.idcaixa = a.idcaixa ´ +
                  ´ and c.id_loja = b.idloja ´+
                  ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
                  ´ group by a.idcaixa, b.nmcaixa, c.nmloja ´+
                  ´ order by 4,5,6,7,8,9,10,11 desc ´;
      ParamByName(´pdtIn´).asDate := DataIn;
      ParamByName(´pdtFn´).AsDate := DataFn;
      Open;
    end;
  end;



GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Preciso fazer a soma mesmo pra saber quem errou mais dentro daqueles campos.

Sobe...


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

02/11/2008

a forma que eu achei foi refazer a soma...
var
  DataIn, DataFn : TDate;
begin
  inherited;
  if RadioButton2.Checked = True then
  begin
    {Passando as datas para variaveis}
    DataIn := StrToDate(MaskEdit1.Text);
    DataFn := StrToDate(MaskEdit2.Text);
    with IBQListCaixa do
    begin
      Close;
      Sql.Clear;
      Sql.Text := ´ select a.idcaixa, b.nmcaixa, c.nmloja, ´+
                  ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdnaofinalizado, ´+
                  ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as CxNaoInformado, ´+
                  ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as InversaoPgto, ´ +
                  ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vdfinaldeumdiapoutro, ´ +
                  ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as cxinfemdterrada, ´ +
                  ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as vlinformadocorretamente, ´ +
                  ´ sum(case when coalesce(a.sangriaincorreta,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as sangriaincorreta, ´ +
                  ´ sum(case when coalesce(a.outrostperros,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as outrostperros, ´ +

                  //*** total de erros. esse será o campo usado no order by ***//
                  ´ sum(case when coalesce(a.vdnaofinalizada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´+
                  ´ sum(case when coalesce(a.cxnaoinformado,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´+
                  ´ sum(case when coalesce(a.inversaopgto,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´ +
                  ´ sum(case when coalesce(a.vdfinaldeumdiapoutro,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´ +
                  ´ sum(case when coalesce(a.cxinfemdterrada,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´ +
                  ´ sum(case when coalesce(a.vlinformadocorretamente,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´ +
                  ´ sum(case when coalesce(a.sangriaincorreta,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) + ´ +
                  ´ sum(case when coalesce(a.outrostperros,´´F´´) = ´´V´´ ´+
                  ´          then 1 ´+
                  ´          else 0 end) as total_de_erros ´ +

                  ´ from  movimento a, respcaixa b, lojas c ´+
                  ´ where b.idcaixa = a.idcaixa ´ +
                  ´ and c.id_loja = b.idloja ´+
                  ´ and a.dtmovimento between :pdtIn and :pdtFn ´+
                  ´ group by a.idcaixa, b.nmcaixa, c.nmloja ´+
                  ´ order by 12 desc ´;
      ParamByName(´pdtIn´).asDate := DataIn;
      ParamByName(´pdtFn´).AsDate := DataFn;
      Open;
    end;
  end;



GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Olá Emerson, ja melhorou bastante, esta ordenando pela soma, só mais uma duvida.

Tem como eu jogar o total, por nome deste select em um novo campo também?

Tipo assim

fulano---total erros 10
ciclano--total erros 8
beltrano---total erros 5

Isso tudo no mesmo select

É que a ideia seria tirar um relatorio num determinado período e em baixo neste relatorio um total

Grato
Adriano


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Olá Emerson, ja melhorou bastante, esta ordenando pela soma, só mais uma duvida. Tem como eu jogar o total, por nome deste select em um novo campo também? Tipo assim fulano---total erros 10 ciclano--total erros 8 beltrano---total erros 5 Isso tudo no mesmo select É que a ideia seria tirar um relatorio num determinado período e em baixo neste relatorio um total Grato Adriano
Será que tem como gerar um total geral neste select?

Sobe...


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Pessoal, alguém sabe se pelo menos teria alguma forma de somar o total de cada um? Independente de ser no mesmo select? Ou seja em um outro select, não estou sabendo motar esta soma.


GOSTEI 0
Adriano_servitec

Adriano_servitec

02/11/2008

Consegui resolver, valeu Emerson, obrigado pela ajuda amigo.


GOSTEI 0
POSTAR