how to export TADODataSet with Fields Texts not Fields Values

百般思念 提交于 2019-12-11 08:06:48

问题


I have a TADODataSet connected with a stored procedure which produce 40 Columns * 800 Row the TADODataSet has an AfterOpen event which assign an OnGetText for it is Fields like :

procedure TForm1.ADODataSet1AfterOpen(DataSet: TDataSet);
begin
  with DataSet do 
  begin
    Fields[4].DisplayLabel:=TR(AS2); //RefId
    Fields[4].DisplayWidth:=8;
    Fields[4].Tag:=1;
    Fields[4].OnGetText:=RefGetText;

    Fields[5].DisplayLabel:=TR(AS3); //ClientId
    Fields[5].DisplayWidth:=8;
    Fields[5].Tag:=1;
    Fields[5].OnGetText:=ClientGetText;
  end;
end;


procedure TForm1.RefGetText(Sender: TField; var Text: String; DisplayText:   Boolean);
begin
  if Sender.DataSet.FieldByName('RelStoreId').AsString='' then
    Text:='NO REF ID'
  else
    KHDM.RefGetText(Sender,Text,DisplayText);
end;

procedure TForm1.ClientGetText(Sender: TField; var Text: String; DisplayText:   Boolean);
begin
  if Sender.DataSet.FieldByName('ClientId').AsString='' then
    Text:='Client ID is not Assigned'
  else
    KHDM.ClientGetText(Sender,Text,DisplayText);
end;

I want to export the data to an XML with the texts I don't want to make a loop on fields and records because it is very slow I want something like bulk copy to stream or something like that

I cannot change the way I'm working because there are around 800 module which using the same way...

please help.


回答1:


There is not much you can do to optimize this, since you don't want to make too many changes.

I hope you can optimize this: If your dataset has fixed fields (added in design time), you can reference the field using the component field, which is usually named as DataSetNameFieldName, (for instance cdsEmployeeEMPNO).

If that is the case, you can reference cdsEmployeeEMPNO.AsString (or whatever property you need). The reason this is faster, is because the field component you use in this case, already knows which field it refers to.

In your case, you use a lookup by name: if Sender.DataSet.FieldByName('RelStoreId').AsString=.. This means that each and every time, the code performs DataSet.Fields.IndexOf(FieldName). This is a slow lookup, because those fields aren't sorted or anything. Given the size of your dataset, this can be thousands of such lookups, which can easily be twice as fast if you do it smarter.

If, for some reason, you cannot use these field component wrappers, you can also perform the lookup once, store the indexes of the fields you need in variables in your datamodule and request the value like this: if Sender.DataSet.Fields[RelStoreIdIndex].AsString= You now use the index of the field directly, which saves the lookup. This will make it a little faster.

Note however that XML outputting is slow as well. You don't show any code of the export, but maybe there could be some serious possibilities for optimization there. It's always good to do some profiling on various parts of your code to find the actual bottleneck, before you start refactoring everything.




回答2:


I have used this kind of technique before - Any Help to you ? I can see the length of the output is a problem but you might be able to fettle it somehow. Perhaps look at the ClientDataset.SavetoFile() Method

function DataSetToXml(const ADataSet : TOraQuery) : String;
var
  Provider : TDataSetProvider;
  ClientDataSet : TClientDataset;
begin
  Provider := TDataSetProvider.Create(nil);
  try
    Provider.Name := 'tmpProvider';
    Provider.DataSet := ADataSet;
    ClientDataSet := TClientDataSet.Create(nil);
    try
      ClientDataSet.Data := Provider.Data;
      Result := ClientDataSet.XMLData;
    finally
      FreeAndNil(ClientDataSet);
    end;
  finally
    FreeAndNil(Provider);
  end;
end;


来源:https://stackoverflow.com/questions/13605901/how-to-export-tadodataset-with-fields-texts-not-fields-values

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!