我想在Delphi中做一个类似多维关联数组的数据结构。
我知道有TObjectDictionary
。但是用TObjectDictionary制作多维数组是如此困难,而且我认为效率不高。
在Delphi中是否有其他好的方法来制作多维关联数组?
TDictionary是基于哈希的,因此无论维度多少,性能都不会严重下降。二维版本的字典可以这样实现:
T2DimDictionary<TDim1,TDim2,TValue> = class
private
function GetValue(x: TDim1; y: TDim2): TValue;
procedure SetValue(x: TDim1; y: TDim2; const Value: TValue);
protected
FDictionary: TObjectDictionary<TDim1, TDictionary<TDim2, TValue>>;
public
constructor Create;
destructor Destroy; override;
property Values[x: TDim1; y: TDim2]: TValue read GetValue write SetValue; default;
end;
{ T2DimDictionary }
constructor T2DimDictionary<TDim1,TDim2,TValue>.Create;
begin
FDictionary := TObjectDictionary<TDim1, TDictionary<TDim2, TValue>>.Create;
end;
destructor T2DimDictionary<TDim1,TDim2,TValue>.Destroy;
begin
FreeAndNil(FDictionary);
inherited;
end;
function T2DimDictionary<TDim1,TDim2,TValue>.GetValue(x: TDim1; y: TDim2): TValue;
var
SubArray: TDictionary<TDim2, TValue>;
begin
if not FDictionary.TryGetValue(x, SubArray) or
not SubArray.TryGetValue(y, result)
then
raise exception.Create('Error');
end;
procedure T2DimDictionary<TDim1,TDim2,TValue>.SetValue(x: TDim1; y: TDim2;
const Value: TValue);
var
SubArray: TDictionary<TDim2, TValue>;
begin
if not FDictionary.TryGetValue(x, SubArray) then
begin
SubArray := TDictionary<TDim2, TValue>.Create;
FDictionary.Add(x, SubArray);
end;
SubArray.AddOrSetValue(y, Value);
end;
var
d: T2DimDictionary<integer, string, string>;
begin
d := T2DimDictionary<integer, string, string>.Create;
d[1,'january'] := 'test1';
d[1,'march'] := 'test2';
assert(d[1,'january']='test1');
FreeAndNil(d);
end;
或者,您可以使用基于所有"维度"的复杂键的单个TDictionary。