I have an application which uses client datasets as in memory tables, and local archive for data received from laboratory instruments. Over time, I've added a few fields to these client datasets, and in order to keep the saved data accessible, I've written a small procedure which literally updates the old saved files. So far it has been working perfectly. Recently, I had to use nested datasets, and I tried to change my code to iterate through nested datasets and update them as well. The code I've come up with so far is this:
procedure UpdateCDS(NewCDS: TClientDataSet; const OldFileName: string);
procedure InternalUpdateCDS(NewCDS, OldCDS: TClientDataSet);
var
i, j: Integer;
NewNestedCDS, OldNestedCDS: TClientDataSet;
begin
OldCDS.First;
while not OldCDS.Eof do
begin
NewCDS.Append;
for i := 0 to NewCDS.FieldDefs.Count - 1 do
if NewCDS.Fields[i].FieldKind = fkData then
for j := 0 to OldCDS.Fields.Count - 1 do
if UpperCase(NewCDS.Fields[i].FieldName)
= UpperCase(OldCDS.Fields[j].FieldName) then
begin
if not OldCDS.Fields[j].IsNull then
if OldCDS.Fields[j].DataType <> ftDataSet then
NewCDS.Fields[i].Value := OldCDS.Fields[j].Value
else
begin
NewNestedCDS := TClientDataSet.Create(nil);
try
OldNestedCDS := TClientDataSet.Create(nil);
try
OldNestedCDS.DataSetField :=
TDataSetField(OldCDS.Fields[j]);
NewNestedCDS.DataSetField :=
TDataSetField(NewCDS.Fields[i]);
OldNestedCDS.Open;
NewNestedCDS.Open;
InternalUpdateCDS(NewNestedCDS, OldNestedCDS);
finally
OldNestedCDS.Free;
end;
finally
NewNestedCDS.Free;
end;
end;
Break;
end;
NewCDS.Post;
OldCDS.Next;
end;
NewCDS.MergeChangeLog;
end;
var
OldCDS: TClientDataSet;
begin
OldCDS := TClientDataSet.Create(nil);
try
OldCDS.LoadFromFile(OldFileName);
InternalUpdateCDS(NewCDS, OldCDS);
finally
OldCDS.Free;
end;
end;
My problem is, this code is way too slow. For 1000 records, it takes about 10 seconds on my intel T7500. Is there a faster way to update a client dataset?