更轻松地使用数组

时间:2009-02-27 19:03:54

标签: delphi

我有以下情况:

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;

我很懒,这对我来说太过分了......我想要一个更简单的方法来做这个,任何想法?

6 个答案:

答案 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没有更简单的方法,但有两件事可以让你的生活更轻松:

  1. 编写自己的DataSetToArray函数。 (正如其他答案所建议的那样)
  2. 如果您使用的是Delphi 2007或更新版本,则可以使用帮助程序类向数据集添加ToArray函数:

    TDataSetHelper = class helper for TDataSet
      function ToArray: TStringArray;
    end;
    
  3. 这样你的所有数据集都有这个功能,你可以使用:

    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时释放它。