Usar Case When em ClientDataSet.Filter Delphi

Delphi

25/02/2019

Tenho uma situação onde preciso usar um Case When no filtro do meu ClientDataSet, alguém já passou por isso ou tem alguma sugestão?
Tentei utilizar da forma como se escreve a query, mas ele aponta erro "field 'case' not found".
Desde já agradeço.

strFiltro := 'cd_Produto = ' + cds_ArqCodPro.AsString; 
      strFiltro := strFiltro + ' and case when [ds_SerieNF] is not null then [ds_SerieNF] else '' end = case when [ds_SerieNF] is not null then ' + QuotedStr(cds_Arq029SerNot.AsString) + ' else '' end'; 
      strFiltro := strFiltro + ' and case when [cd_Fornecedor] > 0 then [cd_Fornecedor] else 0 end = case when [cd_Fornecedor] > 0 then ' + cds_Arq029CodEmi.AsString + ' else 0 end'; 
      strFiltro := strFiltro + ' and case when [cd_SequenciaItem] > 0 then [cd_SequenciaItem] else 0 end = case when [cd_SequenciaItem] > 0 then ' + cds_Arq029SeqIte.AsString + ' else 0 end'; 

      cds_Lote.Filtered := False; 
      cds_Lote.Filter := strFiltro; 
      cds_Lote.Filtered := True; 
      cds_Lote.First;
Wesley Aip

Wesley Aip

Curtidas 0

Melhor post

Emerson Nascimento

Emerson Nascimento

25/02/2019

No meu banco, pode ser que eu tenha os seguintes registros:
Lote 'ABC123', cd_Produto = 10, ds_SerieNF = null, cd_Fornecedor = 0, cd_SequenciaItem = 0
Lote 'XYZ987', cd_Produto = 10, ds_SerieNF = 'S-1' cd_Fornecedor = 244, cd_SequenciaItem = 1
Se eu usar o "or", da forma como sugeriu, não vai me retornar as duas linhas?


Depende. Pelo que eu entedi, você está fazendo o seguinte:
strFiltro := strFiltro + ' and case when [ds_SerieNF] is not null then [ds_SerieNF] else '' end = case when [ds_SerieNF] is not null then ' + QuotedStr(cds_Arq029SerNot.AsString) + ' else '' end';

supondo que cds_Arq029SerNot.AsString='S-1', a linha acima terá o seguinte resultado:
and case when [ds_SerieNF] is not null then [ds_SerieNF] else '' end = case when [ds_SerieNF] is not null then 'S-1' else '' end

que, no motor do banco de dados, passando pelo primeiro registro, seria algo assim:
and '' = ''
, porque [ds_SerieNF ] é nulo. ou seja: o registro faria parte do resultset.

da forma como eu passei seria:
and ([ds_SerieNF] IS NULL OR [ds_SerieNF] = 'S-1')
, ou seja: o registro faria parte do resultset, porque [ds_SerieNF ] é nulo.

o resultado, ao meu ver, seria o mesmo.


GOSTEI 1

Mais Respostas

Emerson Nascimento

Emerson Nascimento

25/02/2019

tente assim:
strFiltro := '[cd_Produto] = ' + cds_ArqCodPro.AsString; 
strFiltro := strFiltro + ' and ([ds_SerieNF] IS NULL OR [ds_SerieNF] = '+QuotedStr(cds_Arq029SerNot.AsString)+');
strFiltro := strFiltro + ' and ([cd_Fornecedor] = 0 OR [cd_Fornecedor] = ' + cds_Arq029CodEmi.AsString + ')'; 
strFiltro := strFiltro + ' and ([cd_SequenciaItem] = 0 OR [cd_SequenciaItem] = ' + cds_Arq029SeqIte.AsString + ')'; 


GOSTEI 0
Emerson Nascimento

Emerson Nascimento

25/02/2019

tente assim:
strFiltro := 'cd_Produto = ' + cds_ArqCodPro.AsString; 
strFiltro := strFiltro + ' and ([ds_SerieNF] IS NULL OR [ds_SerieNF] = '+QuotedStr(cds_Arq029SerNot.AsString)+')';
strFiltro := strFiltro + ' and ([cd_Fornecedor] = 0 OR [cd_Fornecedor] = ' + cds_Arq029CodEmi.AsString + ')'; 
strFiltro := strFiltro + ' and ([cd_SequenciaItem] = 0 OR [cd_SequenciaItem] = ' + cds_Arq029SeqIte.AsString + ')'; 
GOSTEI 0
Wesley Aip

Wesley Aip

25/02/2019

tente assim:
strFiltro := 'cd_Produto = ' + cds_ArqCodPro.AsString; 
strFiltro := strFiltro + ' and ([ds_SerieNF] IS NULL OR [ds_SerieNF] = '+QuotedStr(cds_Arq029SerNot.AsString)+')';
strFiltro := strFiltro + ' and ([cd_Fornecedor] = 0 OR [cd_Fornecedor] = ' + cds_Arq029CodEmi.AsString + ')'; 
strFiltro := strFiltro + ' and ([cd_SequenciaItem] = 0 OR [cd_SequenciaItem] = ' + cds_Arq029SeqIte.AsString + ')'; 

Obrigado pela resposta Emerson.

No meu banco, pode ser que eu tenha os seguintes registros:
Lote 'ABC123', cd_Produto = 10, ds_SerieNF = null, cd_Fornecedor = 0, cd_SequenciaItem = 0
Lote 'XYZ987', cd_Produto = 10, ds_SerieNF = 'S-1' cd_Fornecedor = 244, cd_SequenciaItem = 1
Se eu usar o "or", da forma como sugeriu, não vai me retornar as duas linhas?
GOSTEI 0
Wesley Aip

Wesley Aip

25/02/2019

No meu banco, pode ser que eu tenha os seguintes registros:
Lote 'ABC123', cd_Produto = 10, ds_SerieNF = null, cd_Fornecedor = 0, cd_SequenciaItem = 0
Lote 'XYZ987', cd_Produto = 10, ds_SerieNF = 'S-1' cd_Fornecedor = 244, cd_SequenciaItem = 1
Se eu usar o "or", da forma como sugeriu, não vai me retornar as duas linhas?


Depende. Pelo que eu entedi, você está fazendo o seguinte:
strFiltro := strFiltro + ' and case when [ds_SerieNF] is not null then [ds_SerieNF] else '' end = case when [ds_SerieNF] is not null then ' + QuotedStr(cds_Arq029SerNot.AsString) + ' else '' end';

supondo que cds_Arq029SerNot.AsString='S-1', a linha acima terá o seguinte resultado:
and case when [ds_SerieNF] is not null then [ds_SerieNF] else '' end = case when [ds_SerieNF] is not null then 'S-1' else '' end

que, no motor do banco de dados, passando pelo primeiro registro, seria algo assim:
and '' = ''
, porque [ds_SerieNF ] é nulo. ou seja: o registro faria parte do resultset.

da forma como eu passei seria:
and ([ds_SerieNF] IS NULL OR [ds_SerieNF] = 'S-1')
, ou seja: o registro faria parte do resultset, porque [ds_SerieNF ] é nulo.

o resultado, ao meu ver, seria o mesmo.




Emerson, me confundi num outro select aqui... Realmente está correto.
Eu estava fazendo um teste via query, mas não estava usando as mesmas condições, por isso me equivoquei.
Obrigado pela ajuda!
GOSTEI 0
POSTAR