Pergunta

Cenário:

Quero adicionar um campo calculado ao conjunto de dados (qualquer) em tempo de execução. Não conheço nenhuma outra maneira de obter uma estrutura de conjunto de dados além de executar DataSet.Open método.

Mas o Open O método faz com que, pelo menos, uma linha de dados precise ser transferida do servidor para o cliente. Então eu preciso fechar o conjunto de dados, adicionar campo e reabri -lo. Esta é uma sobrecarga desnecessária na minha opinião. Existe um jeito melhor de fazer isso? Não que eu queira adicionar um campo calcado a qualquer conjunto de dados e não conheço sua estrutura antes da abertura.

No pseudocódigo, é assim:

DataSet.Open;
DataSet.Close;
RecreateFieldsStructure;
AddCalculatedField;
DataSet.Open;

Obrigado pelo seu tempo.

Foi útil?

Solução

Você pode usar o método DataSet.FieldDefs.Update. Isso ainda envolverá alguma transferência de dados, mas nenhuma linha será buscada. Você pode chamar esse método no evento anterior do TDataset e também adicionar os campos calculados lá.

Aqui está um pequeno exemplo que funciona para mim:

procedure TDataModule.cdsExampleBeforeOpen(DataSet: TDataSet);
var I: Integer;
    TmpField: TDateTimeField;
begin
  // Get field definitions from the server
  DataSet.FieldDefs.Update;

  // Add calculated field
  TmpField := TDateTimeField.Create(DataSet);
  with TmpField do
  begin
    Name := 'Date';
    FieldName := 'Date';
    DisplayLabel := 'Date';
    DisplayFormat := 'ddd ddddd';
    Calculated := True;
  end;
  TmpField.DataSet := DataSet;

  // Create fields from field definitions
  for I := 0 to DataSet.FieldDefs.Count - 1 do
    DataSet.FieldDefs[I].CreateField(DataSet);
end;

Outras dicas

Se eu entendi bem sua pergunta; Você deseja ver/conhecer a estrutura das tabelas antes de chamar o método Adoquery (aberto). Se isso quiser, você pode usar os métodos de adoconexão como (getFieldNames) e aqui um exemplo de como obter os nomes de campo da tabela (EMP):

procedure TForm2.Button1Click(Sender: TObject);
var
  lstFields: TStringList;
begin
  lstFields := TStringList.Create;
  try
    ADOConnection1.GetFieldNames('EMP', lstFields);
  finally
    lstFields.Free;
  end;
end;

Em seguida, todos os nomes dos campos estão agora em (Lstfields). Espero que isso ajude.

Cumprimentos.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top