我有以下情况:
procedure SomeMethod(SomeList: array of string);
我必须使用DataSet中的一些ID调用此方法,我知道我可以这样做:
var
MyArray: array of string;
I: Integer;
begin
SetLength(MyArray, MyDataSet.RecordCount);
I := 0;
MyDataSet.First;
while not MyDataSet.Eof do
begin
MyArray[I] := MyDataSetID.Value;
Inc(I);
MyDataSet.Next;
end;
SomeMethod(MyArray);
end;
我很懒,这对我来说太过分了......我想要一个更简单的方法来做这个,任何想法?
答案 0 :(得分:2)
这是我能想到的唯一方法。但是,为什么你不能把你已经拥有的东西变成一个功能呢?你需要在需要时调用它。
如果您需要将其与不同的数据集一起使用,只需传递数据集和字段以用作参数:
procedure FieldToArray(const DS: TDataSet; const FieldName: string;
const Arr: TStringArray);
var
i: Integer;
begin
SetLength(Arr, DS.RecordCount);
i := 0;
DS.First;
while not DS.Eof do
begin
Arr[i] := DS.FieldByName(FieldName).AsString;
Inc(i);
DS.Next;
end;
end;
某处可见(可能在声明此函数的单元的接口部分中),声明TStringArray类型:
type
TStringArray = array of string;
现在,在您的代码中,您需要任何字段值列表:
var
MyArray: TStringArray;
FieldToArray(MyDataSet, 'ID', MyArray);
SomeProc(MyArray);
FieldToArray(AnotherDataSet, 'LastName', MyArray);
SomeOtherProc(MyArray);
MyArray := nil;
答案 1 :(得分:1)
除了Ken White的回答。反复调用FieldByName可能会造成严重的性能损失。因此,您可以使用变量来存储字段(使用数据集更新)。
procedure FieldToArray(const DS: TDataSet; const FieldName: string;
const Arr: TStringArray);
var
i: Integer;
field : TField;
begin
SetLength(Arr, DS.RecordCount);
i := 0;
DS.First;
field := DS.FieldByName(FieldName);
while not DS.Eof do
begin
Arr[i] := field.AsString;
DS.Next;
Inc(i);
end;
end;
答案 2 :(得分:1)
据我所知,Delphi没有更简单的方法,但有两件事可以让你的生活更轻松:
DataSetToArray
函数。 (正如其他答案所建议的那样)如果您使用的是Delphi 2007或更新版本,则可以使用帮助程序类向数据集添加ToArray
函数:
TDataSetHelper = class helper for TDataSet
function ToArray: TStringArray;
end;
这样你的所有数据集都有这个功能,你可以使用:
SomeMethod(MyDataset.ToArray);
答案 3 :(得分:0)
我建议永远不要使用 TDataSet.RecordCount ,除非您知道完全数据在任何给定时间可能会如何变化,以及您将来会使用哪种数据访问权限。首先获取记录数然后循环它们有以下问题:
如果在一个事务中没有执行此操作,则在执行循环时可能会更改记录数。这可能导致严重的崩溃 - 阵列实际上可能太短。
如果SQL服务器位于 TDataSet 之后,那么您最终可能会获取两次结果集,一次用于获取记录数,然后用于获取数据。
由于这个原因,我没有看到在 TStrings 对象上使用字符串数组的好处。在循环中调用 TStrings.Add()是关于你可以拥有的最短代码。
答案 4 :(得分:0)
我也是一个懒惰的程序员。我曾经被聘用为VB6程序员,我喜欢他们所有的CInt,CStr,CSomethingOrOther功能,我在我自己的公共单元中设置了一些类似的功能。我做的第一个是CArray功能,我使用 OVERRIDE 声明制作了几个版本。我有一个用于StringLists,一个用于分隔字符串,还有一个用于数据集。所以我可能会做类似
的事情 while not DS.Eof do
begin
MyValue := CArray(DS)[4];
DS.Next;
end;
我对此作了一点欺骗,因为我使用了该字段的索引。所以我的解决方案在这方面很糟糕,但是能够在很多不同场景中使用CArray是很好的,它可以将StringLists和数据集之类的东西变成可以监视的东西,并在你到达时查看具体价值。
答案 5 :(得分:0)
它绝对必须是“一串字符串”吗?几乎任何你可以使用动态数组做的事情,你可以使用List并更容易地做。我就是这样做的
procedure SomeMethod(SomeList: TStringList);
...
var
MyList: TStringList;
begin
MyList := TStringList.Create;
MyDataSet.First;
while not MyDataSet.Eof do
begin
MyList.add(MyDataSetID.Value);
MyDataSet.Next;
end;
SomeMethod(MyList);
end;
当然,确保在完成TStringList时释放它。